Permalink
Browse files

ae-imports: Remove unneeded thread stuff in native code.

ae-imports does not create any threads from native code, so this thread
attach/detach business is pointless, messy, and a potential source of
bugs.  It might even be against spec.
  • Loading branch information...
littleguy77 committed Feb 18, 2015
1 parent ff76c34 commit ee3fa7e5ad8ccac84c6410925263e4fa1d9f556a
Showing with 3 additions and 77 deletions.
  1. +3 −77 jni/ae-bridge/ae_imports.cpp
@@ -19,15 +19,13 @@
* Authors: Paul Lamb, littleguy77
*/
#include <pthread.h>
#include "SDL.h"
#include "ae_imports.h"
/*******************************************************************************
Globals used internally
*******************************************************************************/
static pthread_key_t mThreadKey;
static JavaVM* mJavaVM;
// Imported java class reference
@@ -36,87 +34,14 @@ static jclass mActivityClass;
// Imported java method references
static jmethodID midStateCallback;
/*******************************************************************************
Functions called internally
*******************************************************************************/
static void Android_JNI_ThreadDestroyed(void* value)
{
/* The thread is being destroyed, detach it from the Java VM and set the mThreadKey value to NULL as required */
JNIEnv *env = (JNIEnv*) value;
if (env != NULL)
{
mJavaVM->DetachCurrentThread();
pthread_setspecific(mThreadKey, NULL);
}
}
static JNIEnv* Android_JNI_GetEnv(void)
{
/* From http://developer.android.com/guide/practices/jni.html
* All threads are Linux threads, scheduled by the kernel.
* They're usually started from managed code (using Thread.start), but they can also be created elsewhere and then
* attached to the JavaVM. For example, a thread started with pthread_create can be attached with the
* JNI AttachCurrentThread or AttachCurrentThreadAsDaemon functions. Until a thread is attached, it has no JNIEnv,
* and cannot make JNI calls.
* Attaching a natively-created thread causes a java.lang.Thread object to be constructed and added to the "main"
* ThreadGroup, making it visible to the debugger. Calling AttachCurrentThread on an already-attached thread
* is a no-op.
* Note: You can call this function any number of times for the same thread, there's no harm in it
*/
JNIEnv *env;
int status = mJavaVM->AttachCurrentThread(&env, NULL);
if (status < 0)
{
return 0;
}
return env;
}
static int Android_JNI_SetupThread(void)
{
/* From http://developer.android.com/guide/practices/jni.html
* Threads attached through JNI must call DetachCurrentThread before they exit. If coding this directly is awkward,
* in Android 2.0 (Eclair) and higher you can use pthread_key_create to define a destructor function that will be
* called before the thread exits, and call DetachCurrentThread from there. (Use that key with pthread_setspecific
* to store the JNIEnv in thread-local-storage; that way it'll be passed into your destructor as the argument.)
* Note: The destructor is not called unless the stored value is != NULL
* Note: You can call this function any number of times for the same thread, there's no harm in it
* (except for some lost CPU cycles)
*/
JNIEnv *env = Android_JNI_GetEnv();
pthread_setspecific(mThreadKey, (void*) env);
return 1;
}
/*******************************************************************************
Functions called automatically by JNI framework
*******************************************************************************/
// Library init
extern jint JNI_OnLoad(JavaVM* vm, void* reserved)
{
JNIEnv *env;
mJavaVM = vm;
if (mJavaVM->GetEnv((void**) &env, JNI_VERSION_1_4) != JNI_OK)
{
return -1;
}
/*
* Create mThreadKey so we can keep track of the JNIEnv assigned to each thread
* Refer to http://developer.android.com/guide/practices/design/jni.html for the rationale behind this
*/
if (pthread_key_create(&mThreadKey, Android_JNI_ThreadDestroyed))
{
LOGE("Error initializing pthread key");
}
else
{
Android_JNI_SetupThread();
}
return JNI_VERSION_1_4;
}
@@ -128,7 +53,6 @@ extern DECLSPEC void Android_JNI_InitImports(JNIEnv* env, jclass cls)
{
LOGI("Android_JNI_InitImports()");
Android_JNI_SetupThread();
mActivityClass = (jclass) env->NewGlobalRef(cls);
midStateCallback = env->GetStaticMethodID(mActivityClass, "stateCallback", "(II)V");
if (!midStateCallback)
@@ -160,6 +84,8 @@ extern DECLSPEC void Android_JNI_StateCallback(void* context, m64p_core_param pa
* (successful) 1
* (unsuccessful) 0
*/
JNIEnv *env = Android_JNI_GetEnv();
JNIEnv *env;
if (mJavaVM->GetEnv((void**) &env, JNI_VERSION_1_4) != JNI_OK)
return;
env->CallStaticVoidMethod(mActivityClass, midStateCallback, (int) paramChanged, newValue);
}

0 comments on commit ee3fa7e

Please sign in to comment.