This is an automated email from the ASF dual-hosted git repository. markt pushed a commit to branch 8.5.x in repository https://gitbox.apache.org/repos/asf/tomcat.git
The following commit(s) were added to refs/heads/8.5.x by this push: new f8a10090ca Refactor to reduce native calls f8a10090ca is described below commit f8a10090ca893168f7e805fe2eefc1203ed08eea Author: Mark Thomas <ma...@apache.org> AuthorDate: Fri Feb 24 14:59:43 2023 +0000 Refactor to reduce native calls Thread.currentThread() is a native call so ensure it is only used once per method, caching the result in a local variable if it is used more than once. Note: some instances of caching aren't strictly necessary but are a side-effect of the refactoring. --- java/org/apache/catalina/ant/ValidatorTask.java | 7 +- .../core/JreMemoryLeakPreventionListener.java | 7 +- java/org/apache/catalina/core/StandardContext.java | 14 ++-- java/org/apache/catalina/core/StandardServer.java | 5 +- .../catalina/ha/context/ReplicatedContext.java | 7 +- .../apache/catalina/ha/session/DeltaManager.java | 7 +- .../apache/catalina/ha/session/DeltaSession.java | 7 +- java/org/apache/catalina/loader/WebappLoader.java | 7 +- java/org/apache/catalina/realm/JAASRealm.java | 10 +-- java/org/apache/catalina/realm/JNDIRealm.java | 80 +++++++++++++--------- .../apache/catalina/servlets/DefaultServlet.java | 14 ++-- .../tribes/membership/McastServiceImpl.java | 38 +++++----- .../catalina/valves/StuckThreadDetectionValve.java | 5 +- java/org/apache/coyote/AsyncStateMachine.java | 13 ++-- java/org/apache/jasper/JspC.java | 9 +-- .../apache/jasper/compiler/ELFunctionMapper.java | 5 +- .../apache/jasper/compiler/JspDocumentParser.java | 15 ++-- .../apache/jasper/compiler/TagPluginManager.java | 15 ++-- java/org/apache/naming/ContextBindings.java | 10 +-- .../tomcat/util/descriptor/tld/TldParser.java | 13 ++-- .../tomcat/util/security/PrivilegedGetTccl.java | 15 +++- .../tomcat/util/security/PrivilegedSetTccl.java | 1 + .../tomcat/util/threads/ThreadPoolExecutor.java | 6 +- .../tomcat/websocket/AsyncChannelGroupUtil.java | 8 +-- .../tomcat/websocket/server/WsFrameServer.java | 14 ++-- .../TestWebappClassLoaderExecutorMemoryLeak.java | 11 ++- .../catalina/startup/TestTomcatClassLoader.java | 7 +- .../org/apache/juli/TestClassLoaderLogManager.java | 7 +- 28 files changed, 200 insertions(+), 157 deletions(-) diff --git a/java/org/apache/catalina/ant/ValidatorTask.java b/java/org/apache/catalina/ant/ValidatorTask.java index fbe360dd0a..81d3997bc4 100644 --- a/java/org/apache/catalina/ant/ValidatorTask.java +++ b/java/org/apache/catalina/ant/ValidatorTask.java @@ -81,8 +81,9 @@ public class ValidatorTask extends BaseRedirectorHelperTask { } // Commons-logging likes having the context classloader set - ClassLoader oldCL = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(ValidatorTask.class.getClassLoader()); + Thread currentThread = Thread.currentThread(); + ClassLoader oldCL = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(ValidatorTask.class.getClassLoader()); // Called through trusted manager interface. If running under a // SecurityManager assume that untrusted applications may be deployed. @@ -100,7 +101,7 @@ public class ValidatorTask extends BaseRedirectorHelperTask { handleErrorOutput("Validation failure: " + e); } } finally { - Thread.currentThread().setContextClassLoader(oldCL); + currentThread.setContextClassLoader(oldCL); closeRedirector(); } diff --git a/java/org/apache/catalina/core/JreMemoryLeakPreventionListener.java b/java/org/apache/catalina/core/JreMemoryLeakPreventionListener.java index 22b55b8508..a2d6b57ea0 100644 --- a/java/org/apache/catalina/core/JreMemoryLeakPreventionListener.java +++ b/java/org/apache/catalina/core/JreMemoryLeakPreventionListener.java @@ -262,12 +262,13 @@ public class JreMemoryLeakPreventionListener implements LifecycleListener { DriverManager.getDrivers(); } - ClassLoader loader = Thread.currentThread().getContextClassLoader(); + Thread currentThread = Thread.currentThread(); + ClassLoader loader = currentThread.getContextClassLoader(); try { // Use the system classloader as the victim for all this // ClassLoader pinning we're about to do. - Thread.currentThread().setContextClassLoader(ClassLoader.getSystemClassLoader()); + currentThread.setContextClassLoader(ClassLoader.getSystemClassLoader()); /* * Several components end up calling: sun.awt.AppContext.getAppContext() @@ -463,7 +464,7 @@ public class JreMemoryLeakPreventionListener implements LifecycleListener { } } finally { - Thread.currentThread().setContextClassLoader(loader); + currentThread.setContextClassLoader(loader); } } } diff --git a/java/org/apache/catalina/core/StandardContext.java b/java/org/apache/catalina/core/StandardContext.java index aaadf45171..dbd0afc5f8 100644 --- a/java/org/apache/catalina/core/StandardContext.java +++ b/java/org/apache/catalina/core/StandardContext.java @@ -5528,12 +5528,13 @@ public class StandardContext extends ContainerBase implements Context, Notificat webApplicationClassLoader = loader.getClassLoader(); } + Thread currentThread = Thread.currentThread(); if (originalClassLoader == null) { if (usePrivilegedAction) { - PrivilegedAction<ClassLoader> pa = new PrivilegedGetTccl(); + PrivilegedAction<ClassLoader> pa = new PrivilegedGetTccl(currentThread); originalClassLoader = AccessController.doPrivileged(pa); } else { - originalClassLoader = Thread.currentThread().getContextClassLoader(); + originalClassLoader = currentThread.getContextClassLoader(); } } @@ -5546,10 +5547,10 @@ public class StandardContext extends ContainerBase implements Context, Notificat ThreadBindingListener threadBindingListener = getThreadBindingListener(); if (usePrivilegedAction) { - PrivilegedAction<Void> pa = new PrivilegedSetTccl(webApplicationClassLoader); + PrivilegedAction<Void> pa = new PrivilegedSetTccl(currentThread, webApplicationClassLoader); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(webApplicationClassLoader); + currentThread.setContextClassLoader(webApplicationClassLoader); } if (threadBindingListener != null) { try { @@ -5579,11 +5580,12 @@ public class StandardContext extends ContainerBase implements Context, Notificat } } + Thread currentThread = Thread.currentThread(); if (usePrivilegedAction) { - PrivilegedAction<Void> pa = new PrivilegedSetTccl(originalClassLoader); + PrivilegedAction<Void> pa = new PrivilegedSetTccl(currentThread, originalClassLoader); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(originalClassLoader); + currentThread.setContextClassLoader(originalClassLoader); } } diff --git a/java/org/apache/catalina/core/StandardServer.java b/java/org/apache/catalina/core/StandardServer.java index 4b986b9d77..e5708390bb 100644 --- a/java/org/apache/catalina/core/StandardServer.java +++ b/java/org/apache/catalina/core/StandardServer.java @@ -422,9 +422,10 @@ public final class StandardServer extends LifecycleMBeanBase implements Server { // undocumented yet - for embedding apps that are around, alive. return; } + Thread currentThread = Thread.currentThread(); if (getPortWithOffset() == -1) { try { - awaitThread = Thread.currentThread(); + awaitThread = currentThread; while (!stopAwait) { try { Thread.sleep(10000); @@ -448,7 +449,7 @@ public final class StandardServer extends LifecycleMBeanBase implements Server { } try { - awaitThread = Thread.currentThread(); + awaitThread = currentThread; // Loop waiting for a connection and a valid command while (!stopAwait) { diff --git a/java/org/apache/catalina/ha/context/ReplicatedContext.java b/java/org/apache/catalina/ha/context/ReplicatedContext.java index 1eb12975c6..c9f3dfa733 100644 --- a/java/org/apache/catalina/ha/context/ReplicatedContext.java +++ b/java/org/apache/catalina/ha/context/ReplicatedContext.java @@ -106,13 +106,14 @@ public class ReplicatedContext extends StandardContext implements MapOwner { if (loader != null) { classLoader = loader.getClassLoader(); } + Thread currentThread = Thread.currentThread(); if ( classLoader == null ) { - classLoader = Thread.currentThread().getContextClassLoader(); + classLoader = currentThread.getContextClassLoader(); } - if ( classLoader == Thread.currentThread().getContextClassLoader() ) { + if ( classLoader == currentThread.getContextClassLoader() ) { return new ClassLoader[] {classLoader}; } else { - return new ClassLoader[] {classLoader,Thread.currentThread().getContextClassLoader()}; + return new ClassLoader[] {classLoader,currentThread.getContextClassLoader()}; } } diff --git a/java/org/apache/catalina/ha/session/DeltaManager.java b/java/org/apache/catalina/ha/session/DeltaManager.java index 0f8ad8ff22..403a7e9711 100644 --- a/java/org/apache/catalina/ha/session/DeltaManager.java +++ b/java/org/apache/catalina/ha/session/DeltaManager.java @@ -1216,11 +1216,12 @@ public class DeltaManager extends ClusterManagerBase{ * requesting node */ protected void messageReceived(SessionMessage msg, Member sender) { - ClassLoader contextLoader = Thread.currentThread().getContextClassLoader(); + Thread currentThread = Thread.currentThread(); + ClassLoader contextLoader = currentThread.getContextClassLoader(); try { ClassLoader[] loaders = getClassLoaders(); - Thread.currentThread().setContextClassLoader(loaders[0]); + currentThread.setContextClassLoader(loaders[0]); if (log.isDebugEnabled()) { log.debug(sm.getString("deltaManager.receiveMessage.eventType", getName(), msg.getEventTypeString(), sender)); @@ -1261,7 +1262,7 @@ public class DeltaManager extends ClusterManagerBase{ } catch (Exception x) { log.error(sm.getString("deltaManager.receiveMessage.error",getName()), x); } finally { - Thread.currentThread().setContextClassLoader(contextLoader); + currentThread.setContextClassLoader(contextLoader); } } diff --git a/java/org/apache/catalina/ha/session/DeltaSession.java b/java/org/apache/catalina/ha/session/DeltaSession.java index e4371321e9..5cd5329783 100644 --- a/java/org/apache/catalina/ha/session/DeltaSession.java +++ b/java/org/apache/catalina/ha/session/DeltaSession.java @@ -197,16 +197,17 @@ public class DeltaSession extends StandardSession implements Externalizable,Clus public void applyDiff(byte[] diff, int offset, int length) throws IOException, ClassNotFoundException { lockInternal(); try (ObjectInputStream stream = ((ClusterManager) getManager()).getReplicationStream(diff, offset, length)) { - ClassLoader contextLoader = Thread.currentThread().getContextClassLoader(); + Thread currentThread = Thread.currentThread(); + ClassLoader contextLoader = currentThread.getContextClassLoader(); try { ClassLoader[] loaders = getClassLoaders(); if (loaders != null && loaders.length > 0) { - Thread.currentThread().setContextClassLoader(loaders[0]); + currentThread.setContextClassLoader(loaders[0]); } getDeltaRequest().readExternal(stream); getDeltaRequest().execute(this, ((ClusterManager)getManager()).isNotifyListenersOnReplication()); } finally { - Thread.currentThread().setContextClassLoader(contextLoader); + currentThread.setContextClassLoader(contextLoader); } } finally { unlockInternal(); diff --git a/java/org/apache/catalina/loader/WebappLoader.java b/java/org/apache/catalina/loader/WebappLoader.java index 468605f427..f05a2cbf05 100644 --- a/java/org/apache/catalina/loader/WebappLoader.java +++ b/java/org/apache/catalina/loader/WebappLoader.java @@ -290,16 +290,15 @@ public class WebappLoader extends LifecycleMBeanBase @Override public void backgroundProcess() { if (reloadable && modified()) { + Thread currentThread = Thread.currentThread(); try { - Thread.currentThread().setContextClassLoader - (WebappLoader.class.getClassLoader()); + currentThread.setContextClassLoader(WebappLoader.class.getClassLoader()); if (context != null) { context.reload(); } } finally { if (context != null && context.getLoader() != null) { - Thread.currentThread().setContextClassLoader - (context.getLoader().getClassLoader()); + currentThread.setContextClassLoader(context.getLoader().getClassLoader()); } } } diff --git a/java/org/apache/catalina/realm/JAASRealm.java b/java/org/apache/catalina/realm/JAASRealm.java index bb1e9a3017..9c0e120454 100644 --- a/java/org/apache/catalina/realm/JAASRealm.java +++ b/java/org/apache/catalina/realm/JAASRealm.java @@ -385,10 +385,12 @@ public class JAASRealm extends RealmBase { // What if the LoginModule is in the container class loader ? ClassLoader ocl = null; + Thread currentThread = null; if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } try { @@ -402,8 +404,8 @@ public class JAASRealm extends RealmBase { invocationSuccess = false; return null; } finally { - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } diff --git a/java/org/apache/catalina/realm/JNDIRealm.java b/java/org/apache/catalina/realm/JNDIRealm.java index 63026fa99c..5b391ff154 100644 --- a/java/org/apache/catalina/realm/JNDIRealm.java +++ b/java/org/apache/catalina/realm/JNDIRealm.java @@ -1143,6 +1143,7 @@ public class JNDIRealm extends RealmBase { public Principal authenticate(String username, String credentials) { ClassLoader ocl = null; + Thread currentThread = null; JNDIConnection connection = null; Principal principal = null; @@ -1152,8 +1153,9 @@ public class JNDIRealm extends RealmBase { // running on a JVM that includes a fix for // https://bugs.openjdk.java.net/browse/JDK-8273874 if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } // Ensure that we have a directory context available @@ -1215,8 +1217,8 @@ public class JNDIRealm extends RealmBase { } return null; } finally { - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } } @@ -1245,14 +1247,16 @@ public class JNDIRealm extends RealmBase { } ClassLoader ocl = null; + Thread currentThread= null; try { // https://bz.apache.org/bugzilla/show_bug.cgi?id=65553 // This can move back to open() once it is known that Tomcat must be // running on a JVM that includes a fix for // https://bugs.openjdk.java.net/browse/JDK-8273874 if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } if (userPatternArray != null) { @@ -1303,8 +1307,8 @@ public class JNDIRealm extends RealmBase { return new GenericPrincipal(username, credentials, roles); } } finally { - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } } @@ -1318,15 +1322,17 @@ public class JNDIRealm extends RealmBase { @Override public Principal authenticate(String username) { ClassLoader ocl = null; + Thread currentThread = null; try { if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } return super.authenticate(username); } finally { - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } } @@ -1341,15 +1347,17 @@ public class JNDIRealm extends RealmBase { public Principal authenticate(String username, String clientDigest, String nonce, String nc, String cnonce, String qop, String realm, String md5a2) { ClassLoader ocl = null; + Thread currentThread = null; try { if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } return super.authenticate(username, clientDigest, nonce, nc, cnonce, qop, realm, md5a2); } finally { - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } } @@ -1363,15 +1371,17 @@ public class JNDIRealm extends RealmBase { @Override public Principal authenticate(X509Certificate[] certs) { ClassLoader ocl = null; + Thread currentThread = null; try { if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } return super.authenticate(certs); } finally { - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } } @@ -1385,15 +1395,17 @@ public class JNDIRealm extends RealmBase { @Override public Principal authenticate(GSSContext gssContext, boolean storeCred) { ClassLoader ocl = null; + Thread currentThread = null; try { if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } return super.authenticate(gssContext, storeCred); } finally { - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } } @@ -1407,15 +1419,17 @@ public class JNDIRealm extends RealmBase { @Override public Principal authenticate(GSSName gssName, GSSCredential gssCredential) { ClassLoader ocl = null; + Thread currentThread = null; try { if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } return super.authenticate(gssName, gssCredential); } finally { - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } } @@ -2737,6 +2751,7 @@ public class JNDIRealm extends RealmBase { // Check to see if the connection to the directory can be opened ClassLoader ocl = null; + Thread currentThread = null; JNDIConnection connection = null; try { // https://bz.apache.org/bugzilla/show_bug.cgi?id=65553 @@ -2744,8 +2759,9 @@ public class JNDIRealm extends RealmBase { // running on a JVM that includes a fix for // https://bugs.openjdk.java.net/browse/JDK-8273874 if (!isUseContextClassLoader()) { - ocl = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread = Thread.currentThread(); + ocl = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } connection = get(); } catch (NamingException e) { @@ -2756,8 +2772,8 @@ public class JNDIRealm extends RealmBase { containerLog.error(sm.getString("jndiRealm.open"), e); } finally { release(connection); - if (!isUseContextClassLoader()) { - Thread.currentThread().setContextClassLoader(ocl); + if (currentThread != null) { + currentThread.setContextClassLoader(ocl); } } diff --git a/java/org/apache/catalina/servlets/DefaultServlet.java b/java/org/apache/catalina/servlets/DefaultServlet.java index 4e5290fda7..50c34380ae 100644 --- a/java/org/apache/catalina/servlets/DefaultServlet.java +++ b/java/org/apache/catalina/servlets/DefaultServlet.java @@ -1808,19 +1808,19 @@ public class DefaultServlet extends HttpServlet { // Prevent possible memory leak. Ensure Transformer and // TransformerFactory are not loaded from the web application. ClassLoader original; + Thread currentThread = Thread.currentThread(); if (Globals.IS_SECURITY_ENABLED) { - PrivilegedGetTccl pa = new PrivilegedGetTccl(); + PrivilegedGetTccl pa = new PrivilegedGetTccl(currentThread); original = AccessController.doPrivileged(pa); } else { - original = Thread.currentThread().getContextClassLoader(); + original = currentThread.getContextClassLoader(); } try { if (Globals.IS_SECURITY_ENABLED) { - PrivilegedSetTccl pa = - new PrivilegedSetTccl(DefaultServlet.class.getClassLoader()); + PrivilegedSetTccl pa = new PrivilegedSetTccl(currentThread, DefaultServlet.class.getClassLoader()); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader( + currentThread.setContextClassLoader( DefaultServlet.class.getClassLoader()); } @@ -1838,10 +1838,10 @@ public class DefaultServlet extends HttpServlet { throw new ServletException(sm.getString("defaultServlet.xslError"), e); } finally { if (Globals.IS_SECURITY_ENABLED) { - PrivilegedSetTccl pa = new PrivilegedSetTccl(original); + PrivilegedSetTccl pa = new PrivilegedSetTccl(currentThread, original); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(original); + currentThread.setContextClassLoader(original); } } } diff --git a/java/org/apache/catalina/tribes/membership/McastServiceImpl.java b/java/org/apache/catalina/tribes/membership/McastServiceImpl.java index 7b6a8185f3..a610445a3e 100644 --- a/java/org/apache/catalina/tribes/membership/McastServiceImpl.java +++ b/java/org/apache/catalina/tribes/membership/McastServiceImpl.java @@ -398,6 +398,7 @@ public class McastServiceImpl { log.trace("Mcast receive ping from member " + m); } Runnable t = null; + final Thread currentThread = Thread.currentThread(); if (Arrays.equals(m.getCommand(), Member.SHUTDOWN_PAYLOAD)) { if (log.isDebugEnabled()) { log.debug("Member has shutdown:" + m); @@ -406,12 +407,12 @@ public class McastServiceImpl { t = new Runnable() { @Override public void run() { - String name = Thread.currentThread().getName(); + String name = currentThread.getName(); try { - Thread.currentThread().setName("Membership-MemberDisappeared."); + currentThread.setName("Membership-MemberDisappeared."); service.memberDisappeared(m); - }finally { - Thread.currentThread().setName(name); + } finally { + currentThread.setName(name); } } }; @@ -422,17 +423,17 @@ public class McastServiceImpl { t = new Runnable() { @Override public void run() { - String name = Thread.currentThread().getName(); + String name = currentThread.getName(); try { - Thread.currentThread().setName("Membership-MemberAdded."); + currentThread.setName("Membership-MemberAdded."); service.memberAdded(m); - }finally { - Thread.currentThread().setName(name); + } finally { + currentThread.setName(name); } } }; - } //end if - if ( t != null ) { + } + if (t != null) { executor.execute(t); } } @@ -455,9 +456,10 @@ public class McastServiceImpl { Runnable t = new Runnable() { @Override public void run() { - String name = Thread.currentThread().getName(); + Thread currentThread = Thread.currentThread(); + String name = currentThread.getName(); try { - Thread.currentThread().setName("Membership-MemberAdded."); + currentThread.setName("Membership-MemberAdded."); for (ChannelData datum : data) { try { if (datum != null && !member.equals(datum.getAddress())) { @@ -473,8 +475,8 @@ public class McastServiceImpl { log.error(sm.getString("mcastServiceImpl.unableReceive.broadcastMessage"), t); } } - }finally { - Thread.currentThread().setName(name); + } finally { + currentThread.setName(name); } } }; @@ -494,14 +496,14 @@ public class McastServiceImpl { Runnable t = new Runnable() { @Override public void run() { - String name = Thread.currentThread().getName(); + Thread currentThread = Thread.currentThread(); + String name = currentThread.getName(); try { - Thread.currentThread().setName("Membership-MemberExpired."); + currentThread.setName("Membership-MemberExpired."); service.memberDisappeared(member); } finally { - Thread.currentThread().setName(name); + currentThread.setName(name); } - } }; executor.execute(t); diff --git a/java/org/apache/catalina/valves/StuckThreadDetectionValve.java b/java/org/apache/catalina/valves/StuckThreadDetectionValve.java index 8286f84908..7fe9982d71 100644 --- a/java/org/apache/catalina/valves/StuckThreadDetectionValve.java +++ b/java/org/apache/catalina/valves/StuckThreadDetectionValve.java @@ -173,13 +173,14 @@ public class StuckThreadDetectionValve extends ValveBase { // Keeping a reference to the thread object here does not prevent // GC'ing, as the reference is removed from the Map in the finally clause - Long key = Long.valueOf(Thread.currentThread().getId()); + Thread currentThread = Thread.currentThread(); + Long key = Long.valueOf(currentThread.getId()); StringBuffer requestUrl = request.getRequestURL(); if (request.getQueryString() != null) { requestUrl.append('?'); requestUrl.append(request.getQueryString()); } - MonitoredThread monitoredThread = new MonitoredThread(Thread.currentThread(), requestUrl.toString(), + MonitoredThread monitoredThread = new MonitoredThread(currentThread, requestUrl.toString(), interruptThreadThreshold > 0); activeThreads.put(key, monitoredThread); diff --git a/java/org/apache/coyote/AsyncStateMachine.java b/java/org/apache/coyote/AsyncStateMachine.java index 69925dfc0c..3c08c0f7a9 100644 --- a/java/org/apache/coyote/AsyncStateMachine.java +++ b/java/org/apache/coyote/AsyncStateMachine.java @@ -432,27 +432,28 @@ public class AsyncStateMachine { // Execute the runnable using a container thread from the // Connector's thread pool. Use a wrapper to prevent a memory leak ClassLoader oldCL; + Thread currentThread = Thread.currentThread(); if (Constants.IS_SECURITY_ENABLED) { - PrivilegedAction<ClassLoader> pa = new PrivilegedGetTccl(); + PrivilegedAction<ClassLoader> pa = new PrivilegedGetTccl(currentThread); oldCL = AccessController.doPrivileged(pa); } else { - oldCL = Thread.currentThread().getContextClassLoader(); + oldCL = currentThread.getContextClassLoader(); } try { if (Constants.IS_SECURITY_ENABLED) { - PrivilegedAction<Void> pa = new PrivilegedSetTccl(this.getClass().getClassLoader()); + PrivilegedAction<Void> pa = new PrivilegedSetTccl(currentThread, this.getClass().getClassLoader()); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); + currentThread.setContextClassLoader(this.getClass().getClassLoader()); } processor.getExecutor().execute(runnable); } finally { if (Constants.IS_SECURITY_ENABLED) { - PrivilegedAction<Void> pa = new PrivilegedSetTccl(oldCL); + PrivilegedAction<Void> pa = new PrivilegedSetTccl(currentThread, oldCL); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(oldCL); + currentThread.setContextClassLoader(oldCL); } } } else { diff --git a/java/org/apache/jasper/JspC.java b/java/org/apache/jasper/JspC.java index 6ea5918666..c80d1e6224 100644 --- a/java/org/apache/jasper/JspC.java +++ b/java/org/apache/jasper/JspC.java @@ -1294,6 +1294,7 @@ public class JspC extends Task implements Options { } ClassLoader originalClassLoader = null; + Thread currentThread = Thread.currentThread(); try { // set up a scratch/output dir if none is provided @@ -1318,8 +1319,8 @@ public class JspC extends Task implements Options { clctxt.setServletPackageName(targetPackage); } - originalClassLoader = Thread.currentThread().getContextClassLoader(); - Thread.currentThread().setContextClassLoader(loader); + originalClassLoader = currentThread.getContextClassLoader(); + currentThread.setContextClassLoader(loader); clctxt.setClassLoader(loader); clctxt.setClassPath(classPath); @@ -1363,8 +1364,8 @@ public class JspC extends Task implements Options { } throw new JasperException(e); } finally { - if(originalClassLoader != null) { - Thread.currentThread().setContextClassLoader(originalClassLoader); + if (originalClassLoader != null) { + currentThread.setContextClassLoader(originalClassLoader); } } } diff --git a/java/org/apache/jasper/compiler/ELFunctionMapper.java b/java/org/apache/jasper/compiler/ELFunctionMapper.java index 5ec20ef0d7..99a79d0b7e 100644 --- a/java/org/apache/jasper/compiler/ELFunctionMapper.java +++ b/java/org/apache/jasper/compiler/ELFunctionMapper.java @@ -311,11 +311,12 @@ public class ELFunctionMapper { Class<?> clazz; ClassLoader tccl; + Thread currentThread = Thread.currentThread(); if (Constants.IS_SECURITY_ENABLED) { - PrivilegedAction<ClassLoader> pa = new PrivilegedGetTccl(); + PrivilegedAction<ClassLoader> pa = new PrivilegedGetTccl(currentThread); tccl = AccessController.doPrivileged(pa); } else { - tccl = Thread.currentThread().getContextClassLoader(); + tccl = currentThread.getContextClassLoader(); } try { diff --git a/java/org/apache/jasper/compiler/JspDocumentParser.java b/java/org/apache/jasper/compiler/JspDocumentParser.java index 0ad4774b14..54160b3187 100644 --- a/java/org/apache/jasper/compiler/JspDocumentParser.java +++ b/java/org/apache/jasper/compiler/JspDocumentParser.java @@ -1455,20 +1455,19 @@ class JspDocumentParser throws Exception { ClassLoader original; + Thread currentThread = Thread.currentThread(); if (Constants.IS_SECURITY_ENABLED) { - PrivilegedGetTccl pa = new PrivilegedGetTccl(); + PrivilegedGetTccl pa = new PrivilegedGetTccl(currentThread); original = AccessController.doPrivileged(pa); } else { - original = Thread.currentThread().getContextClassLoader(); + original = currentThread.getContextClassLoader(); } try { if (Constants.IS_SECURITY_ENABLED) { - PrivilegedSetTccl pa = - new PrivilegedSetTccl(JspDocumentParser.class.getClassLoader()); + PrivilegedSetTccl pa = new PrivilegedSetTccl(currentThread, JspDocumentParser.class.getClassLoader()); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader( - JspDocumentParser.class.getClassLoader()); + currentThread.setContextClassLoader(JspDocumentParser.class.getClassLoader()); } SAXParserFactory factory = SAXParserFactory.newInstance(); @@ -1500,10 +1499,10 @@ class JspDocumentParser return saxParser; } finally { if (Constants.IS_SECURITY_ENABLED) { - PrivilegedSetTccl pa = new PrivilegedSetTccl(original); + PrivilegedSetTccl pa = new PrivilegedSetTccl(currentThread, original); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(original); + currentThread.setContextClassLoader(original); } } } diff --git a/java/org/apache/jasper/compiler/TagPluginManager.java b/java/org/apache/jasper/compiler/TagPluginManager.java index 9b830c8427..3e95ed80f9 100644 --- a/java/org/apache/jasper/compiler/TagPluginManager.java +++ b/java/org/apache/jasper/compiler/TagPluginManager.java @@ -77,20 +77,19 @@ public class TagPluginManager { TagPluginParser parser; ClassLoader original; + Thread currentThread = Thread.currentThread(); if (Constants.IS_SECURITY_ENABLED) { - PrivilegedGetTccl pa = new PrivilegedGetTccl(); + PrivilegedGetTccl pa = new PrivilegedGetTccl(currentThread); original = AccessController.doPrivileged(pa); } else { - original = Thread.currentThread().getContextClassLoader(); + original = currentThread.getContextClassLoader(); } try { if (Constants.IS_SECURITY_ENABLED) { - PrivilegedSetTccl pa = - new PrivilegedSetTccl(TagPluginManager.class.getClassLoader()); + PrivilegedSetTccl pa = new PrivilegedSetTccl(currentThread, TagPluginManager.class.getClassLoader()); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader( - TagPluginManager.class.getClassLoader()); + currentThread.setContextClassLoader(TagPluginManager.class.getClassLoader()); } parser = new TagPluginParser(ctxt, blockExternal); @@ -110,10 +109,10 @@ public class TagPluginManager { throw new JasperException(e); } finally { if (Constants.IS_SECURITY_ENABLED) { - PrivilegedSetTccl pa = new PrivilegedSetTccl(original); + PrivilegedSetTccl pa = new PrivilegedSetTccl(currentThread, original); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(original); + currentThread.setContextClassLoader(original); } } diff --git a/java/org/apache/naming/ContextBindings.java b/java/org/apache/naming/ContextBindings.java index baf3ce2bdb..9c4895acc2 100644 --- a/java/org/apache/naming/ContextBindings.java +++ b/java/org/apache/naming/ContextBindings.java @@ -142,8 +142,9 @@ public class ContextBindings { throw new NamingException( sm.getString("contextBindings.unknownContext", obj)); } - threadBindings.put(Thread.currentThread(), context); - threadObjectBindings.put(Thread.currentThread(), obj); + Thread currentThread = Thread.currentThread(); + threadBindings.put(currentThread, context); + threadObjectBindings.put(currentThread, obj); } } @@ -156,8 +157,9 @@ public class ContextBindings { */ public static void unbindThread(Object obj, Object token) { if (ContextAccessController.checkSecurityToken(obj, token)) { - threadBindings.remove(Thread.currentThread()); - threadObjectBindings.remove(Thread.currentThread()); + Thread currentThread = Thread.currentThread(); + threadBindings.remove(currentThread); + threadObjectBindings.remove(currentThread); } } diff --git a/java/org/apache/tomcat/util/descriptor/tld/TldParser.java b/java/org/apache/tomcat/util/descriptor/tld/TldParser.java index e31c2fea58..933a13c1ca 100644 --- a/java/org/apache/tomcat/util/descriptor/tld/TldParser.java +++ b/java/org/apache/tomcat/util/descriptor/tld/TldParser.java @@ -52,18 +52,19 @@ public class TldParser { public TaglibXml parse(TldResourcePath path) throws IOException, SAXException { ClassLoader original; + Thread currentThread = Thread.currentThread(); if (Constants.IS_SECURITY_ENABLED) { - PrivilegedGetTccl pa = new PrivilegedGetTccl(); + PrivilegedGetTccl pa = new PrivilegedGetTccl(currentThread); original = AccessController.doPrivileged(pa); } else { - original = Thread.currentThread().getContextClassLoader(); + original = currentThread.getContextClassLoader(); } try (InputStream is = path.openStream()) { if (Constants.IS_SECURITY_ENABLED) { - PrivilegedSetTccl pa = new PrivilegedSetTccl(TldParser.class.getClassLoader()); + PrivilegedSetTccl pa = new PrivilegedSetTccl(currentThread, TldParser.class.getClassLoader()); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(TldParser.class.getClassLoader()); + currentThread.setContextClassLoader(TldParser.class.getClassLoader()); } XmlErrorHandler handler = new XmlErrorHandler(); digester.setErrorHandler(handler); @@ -85,10 +86,10 @@ public class TldParser { } finally { digester.reset(); if (Constants.IS_SECURITY_ENABLED) { - PrivilegedSetTccl pa = new PrivilegedSetTccl(original); + PrivilegedSetTccl pa = new PrivilegedSetTccl(currentThread, original); AccessController.doPrivileged(pa); } else { - Thread.currentThread().setContextClassLoader(original); + currentThread.setContextClassLoader(original); } } } diff --git a/java/org/apache/tomcat/util/security/PrivilegedGetTccl.java b/java/org/apache/tomcat/util/security/PrivilegedGetTccl.java index 11d11a8602..c580cfab50 100644 --- a/java/org/apache/tomcat/util/security/PrivilegedGetTccl.java +++ b/java/org/apache/tomcat/util/security/PrivilegedGetTccl.java @@ -19,10 +19,19 @@ package org.apache.tomcat.util.security; import java.security.PrivilegedAction; public class PrivilegedGetTccl implements PrivilegedAction<ClassLoader> { + private final Thread currentThread; + + @Deprecated + public PrivilegedGetTccl() { + this(Thread.currentThread()); + } + + public PrivilegedGetTccl(Thread currentThread) { + this.currentThread = currentThread; + } + @Override public ClassLoader run() { - return Thread.currentThread().getContextClassLoader(); + return currentThread.getContextClassLoader(); } } - - diff --git a/java/org/apache/tomcat/util/security/PrivilegedSetTccl.java b/java/org/apache/tomcat/util/security/PrivilegedSetTccl.java index 739d915794..188a8ae08e 100644 --- a/java/org/apache/tomcat/util/security/PrivilegedSetTccl.java +++ b/java/org/apache/tomcat/util/security/PrivilegedSetTccl.java @@ -23,6 +23,7 @@ public class PrivilegedSetTccl implements PrivilegedAction<Void> { private final ClassLoader cl; private final Thread t; + @Deprecated public PrivilegedSetTccl(ClassLoader cl) { this(Thread.currentThread(), cl); } diff --git a/java/org/apache/tomcat/util/threads/ThreadPoolExecutor.java b/java/org/apache/tomcat/util/threads/ThreadPoolExecutor.java index 3de34cb387..7ea4c91ad7 100644 --- a/java/org/apache/tomcat/util/threads/ThreadPoolExecutor.java +++ b/java/org/apache/tomcat/util/threads/ThreadPoolExecutor.java @@ -2222,9 +2222,9 @@ public class ThreadPoolExecutor extends AbstractExecutorService { protected boolean currentThreadShouldBeStopped() { - if (threadRenewalDelay >= 0 - && Thread.currentThread() instanceof TaskThread) { - TaskThread currentTaskThread = (TaskThread) Thread.currentThread(); + Thread currentThread = Thread.currentThread(); + if (threadRenewalDelay >= 0 && currentThread instanceof TaskThread) { + TaskThread currentTaskThread = (TaskThread) currentThread; if (currentTaskThread.getCreationTime() < this.lastContextStoppedTime.longValue()) { return true; diff --git a/java/org/apache/tomcat/websocket/AsyncChannelGroupUtil.java b/java/org/apache/tomcat/websocket/AsyncChannelGroupUtil.java index 024d6351e8..dd5c392801 100644 --- a/java/org/apache/tomcat/websocket/AsyncChannelGroupUtil.java +++ b/java/org/apache/tomcat/websocket/AsyncChannelGroupUtil.java @@ -74,11 +74,11 @@ public class AsyncChannelGroupUtil { private static AsynchronousChannelGroup createAsynchronousChannelGroup() { // Need to do this with the right thread context class loader else the // first web app to call this will trigger a leak - ClassLoader original = Thread.currentThread().getContextClassLoader(); + Thread currentThread = Thread.currentThread(); + ClassLoader original = currentThread.getContextClassLoader(); try { - Thread.currentThread().setContextClassLoader( - AsyncIOThreadFactory.class.getClassLoader()); + currentThread.setContextClassLoader(AsyncIOThreadFactory.class.getClassLoader()); // These are the same settings as the default // AsynchronousChannelGroup @@ -98,7 +98,7 @@ public class AsyncChannelGroupUtil { throw new IllegalStateException(sm.getString("asyncChannelGroup.createFail")); } } finally { - Thread.currentThread().setContextClassLoader(original); + currentThread.setContextClassLoader(original); } } diff --git a/java/org/apache/tomcat/websocket/server/WsFrameServer.java b/java/org/apache/tomcat/websocket/server/WsFrameServer.java index d29ea047aa..c40ae31095 100644 --- a/java/org/apache/tomcat/websocket/server/WsFrameServer.java +++ b/java/org/apache/tomcat/websocket/server/WsFrameServer.java @@ -123,24 +123,26 @@ public class WsFrameServer extends WsFrameBase { @Override protected void sendMessageText(boolean last) throws WsIOException { - ClassLoader cl = Thread.currentThread().getContextClassLoader(); + Thread currentThread = Thread.currentThread(); + ClassLoader cl = currentThread.getContextClassLoader(); try { - Thread.currentThread().setContextClassLoader(applicationClassLoader); + currentThread.setContextClassLoader(applicationClassLoader); super.sendMessageText(last); } finally { - Thread.currentThread().setContextClassLoader(cl); + currentThread.setContextClassLoader(cl); } } @Override protected void sendMessageBinary(ByteBuffer msg, boolean last) throws WsIOException { - ClassLoader cl = Thread.currentThread().getContextClassLoader(); + Thread currentThread = Thread.currentThread(); + ClassLoader cl = currentThread.getContextClassLoader(); try { - Thread.currentThread().setContextClassLoader(applicationClassLoader); + currentThread.setContextClassLoader(applicationClassLoader); super.sendMessageBinary(msg, last); } finally { - Thread.currentThread().setContextClassLoader(cl); + currentThread.setContextClassLoader(cl); } } diff --git a/test/org/apache/catalina/loader/TestWebappClassLoaderExecutorMemoryLeak.java b/test/org/apache/catalina/loader/TestWebappClassLoaderExecutorMemoryLeak.java index 638154cc51..8a34b6f756 100644 --- a/test/org/apache/catalina/loader/TestWebappClassLoaderExecutorMemoryLeak.java +++ b/test/org/apache/catalina/loader/TestWebappClassLoaderExecutorMemoryLeak.java @@ -114,16 +114,15 @@ public class TestWebappClassLoaderExecutorMemoryLeak extends TomcatBaseTest { @Override public void run() { + Thread currentThread = Thread.currentThread(); try { - while (!Thread.currentThread().isInterrupted()) { + while (!currentThread.isInterrupted()) { Thread.sleep(20000); - System.out.println(Thread.currentThread().getClass() - + " [" + Thread.currentThread().getName() - + "] executing " + this._id); + System.out.println( + currentThread.getClass() + " [" + currentThread.getName() + "] executing " + this._id); } } catch (InterruptedException e) { - System.out.println(Thread.currentThread().getClass() + " [" - + Thread.currentThread().getName() + "] EXITING"); + System.out.println(currentThread.getClass() + " [" + currentThread.getName() + "] EXITING"); } } } diff --git a/test/org/apache/catalina/startup/TestTomcatClassLoader.java b/test/org/apache/catalina/startup/TestTomcatClassLoader.java index e9292173d5..d1df88c356 100644 --- a/test/org/apache/catalina/startup/TestTomcatClassLoader.java +++ b/test/org/apache/catalina/startup/TestTomcatClassLoader.java @@ -54,10 +54,9 @@ public class TestTomcatClassLoader extends TomcatBaseTest { @Test public void testNonDefaultClassLoader() throws Exception { - ClassLoader cl = new URLClassLoader(new URL[0], - Thread.currentThread().getContextClassLoader()); - - Thread.currentThread().setContextClassLoader(cl); + Thread currentThread = Thread.currentThread(); + ClassLoader cl = new URLClassLoader(new URL[0], currentThread.getContextClassLoader()); + currentThread.setContextClassLoader(cl); Tomcat tomcat = getTomcatInstance(); tomcat.getServer().setParentClassLoader(cl); diff --git a/test/org/apache/juli/TestClassLoaderLogManager.java b/test/org/apache/juli/TestClassLoaderLogManager.java index 674600edf4..b2482af790 100644 --- a/test/org/apache/juli/TestClassLoaderLogManager.java +++ b/test/org/apache/juli/TestClassLoaderLogManager.java @@ -93,9 +93,10 @@ public class TestClassLoaderLogManager { @Test public void testBug66184() throws IOException { final ClassLoader cl = new TestClassLoader(); - final ClassLoader oldCL = Thread.currentThread().getContextClassLoader(); + final Thread currentThread = Thread.currentThread(); + final ClassLoader oldCL = currentThread.getContextClassLoader(); try { - Thread.currentThread().setContextClassLoader(cl); + currentThread.setContextClassLoader(cl); final ClassLoaderLogManager logManager = new ClassLoaderLogManager(); logManager.readConfiguration(); final Logger rootLogger = logManager.getLogger(""); @@ -103,7 +104,7 @@ public class TestClassLoaderLogManager { Assert.assertNull("root logger has a parent", rootLogger.getParent()); Assert.assertEquals(Level.INFO, rootLogger.getLevel()); } finally { - Thread.currentThread().setContextClassLoader(oldCL); + currentThread.setContextClassLoader(oldCL); } } --------------------------------------------------------------------- To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org For additional commands, e-mail: dev-h...@tomcat.apache.org