This is an automated email from the ASF dual-hosted git repository. markt pushed a commit to branch 1.3.x in repository https://gitbox.apache.org/repos/asf/tomcat-native.git
The following commit(s) were added to refs/heads/1.3.x by this push: new e7a329999 Align with 9.0.x e7a329999 is described below commit e7a329999c66948689f450a320d92a06c6ad14e9 Author: Mark Thomas <ma...@apache.org> AuthorDate: Thu Jul 18 09:38:15 2024 +0100 Align with 9.0.x --- java/org/apache/tomcat/jni/Library.java | 55 ++++++++++++++++++++++++++++++--- 1 file changed, 51 insertions(+), 4 deletions(-) diff --git a/java/org/apache/tomcat/jni/Library.java b/java/org/apache/tomcat/jni/Library.java index 218a101b5..c8e62f4a2 100644 --- a/java/org/apache/tomcat/jni/Library.java +++ b/java/org/apache/tomcat/jni/Library.java @@ -17,6 +17,10 @@ package org.apache.tomcat.jni; import java.io.File; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.atomic.AtomicLong; +import java.util.concurrent.locks.ReadWriteLock; +import java.util.concurrent.locks.ReentrantReadWriteLock; public final class Library { @@ -32,6 +36,9 @@ public final class Library { */ private static Library _instance = null; + private static final AtomicLong generation = new AtomicLong(0); + private static final ReadWriteLock cleanUpLock = new ReentrantReadWriteLock(); + private Library() throws Exception { boolean loaded = false; StringBuilder err = new StringBuilder(); @@ -100,12 +107,30 @@ public final class Library { System.loadLibrary(libraryName); } - /* create global TCN's APR pool - * This has to be the first call to TCN library. + /** + * Create Tomcat Native's global APR pool. This has to be the first call to TCN library. */ private static native boolean initialize(); - /* destroy global TCN's APR pool - * This has to be the last call to TCN library. + /** + * Allows for thread safe termination when other threads may be attempting clean-up concurrently with the current + * thread. Waits for any threads currently holding the clean-up lock to release the lock and then calls + * {@link #terminate()}. + */ + public static void threadSafeTerminate() { + cleanUpLock.writeLock().lock(); + try { + terminate(); + } finally { + generation.incrementAndGet(); + cleanUpLock.writeLock().unlock(); + } + } + /** + * Destroys Tomcat Native's global APR pool. This has to be the last call to TCN library. This will destroy any APR + * root pools that have not been explicitly destroyed. + * <p> + * This method should only be used if the caller is certain that all other threads have finished using the native + * library. */ public static native void terminate(); /* Internal function for loading APR Features */ @@ -287,6 +312,28 @@ public final class Library { return initialize(); } + + public static boolean tryCleanUpLock(long cleanupGeneration) { + try { + boolean result = cleanUpLock.readLock().tryLock(0, TimeUnit.SECONDS); + if (result && generation.get() == cleanupGeneration) { + return true; + } + cleanUpLock.readLock().unlock(); + } catch (InterruptedException e) { + // Treated the same way as not getting the lock + } + return false; + } + + public static long getGeneration() { + return generation.get(); + } + + public static void returnCleanUpLock() { + cleanUpLock.readLock().unlock(); + } + /** * Calls System.load(filename). System.load() associates the * loaded library with the class loader of the class that called --------------------------------------------------------------------- To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org For additional commands, e-mail: dev-h...@tomcat.apache.org