diff options
author | Joachim Kuebart <joachim.kuebart@gmail.com> | 2021-08-13 17:26:57 +0200 |
---|---|---|
committer | Joachim Kuebart <joachim.kuebart@gmail.com> | 2022-05-23 17:17:18 +0200 |
commit | b58c554cdee28b1c79ad8a097da63751a237faee (patch) | |
tree | c8846538bc9880c3c6534db6b384c9b14dd5d221 /Lib/java | |
parent | 1ad77e8c9b955dfbf4c7b48890dcf49278b1e422 (diff) | |
download | swig-b58c554cdee28b1c79ad8a097da63751a237faee.tar.gz |
Java: Option to detach from the JVM in the thread destructor.
Diffstat (limited to 'Lib/java')
-rw-r--r-- | Lib/java/director.swg | 28 |
1 files changed, 27 insertions, 1 deletions
diff --git a/Lib/java/director.swg b/Lib/java/director.swg index e911a3da7..f7c4f2d8a 100644 --- a/Lib/java/director.swg +++ b/Lib/java/director.swg @@ -51,6 +51,22 @@ SWIGINTERN int Swig::GetThreadName(char *name, size_t len) { #endif +#if defined(SWIG_JAVA_DETACH_ON_THREAD_END) +#include <pthread.h> +namespace { + + void detach(void* jvm) { + static_cast<JavaVM*>(jvm)->DetachCurrentThread(); + } + + pthread_key_t detachKey; + void makeDetachKey() { + pthread_key_create(&detachKey, detach); + } + +} +#endif + namespace Swig { /* Java object wrapper */ @@ -201,9 +217,19 @@ namespace Swig { #else director_->swig_jvm_->AttachCurrentThread(jenv, &args); #endif + +#if defined(SWIG_JAVA_DETACH_ON_THREAD_END) + // At least on Android 6, detaching after every call causes a memory leak. + // Instead, register a thread desructor and detach only when the thread ends. + // See https://developer.android.com/training/articles/perf-jni#threads + static pthread_once_t once = PTHREAD_ONCE_INIT; + + pthread_once(&once, makeDetachKey); + pthread_setspecific(detachKey, director->swig_jvm_); +#endif } ~JNIEnvWrapper() { -#if !defined(SWIG_JAVA_NO_DETACH_CURRENT_THREAD) +#if !defined(SWIG_JAVA_DETACH_ON_THREAD_END) && !defined(SWIG_JAVA_NO_DETACH_CURRENT_THREAD) // Some JVMs, eg jdk-1.4.2 and lower on Solaris have a bug and crash with the DetachCurrentThread call. // However, without this call, the JVM hangs on exit when the thread was not created by the JVM and creates a memory leak. if (env_status == JNI_EDETACHED) |