summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChristian Strømme <christian.stromme@digia.com>2013-09-24 18:04:14 +0200
committerThe Qt Project <gerrit-noreply@qt-project.org>2013-09-25 20:32:31 +0200
commit1db90754826730dc810b92f9a741243b90ae8da9 (patch)
tree3de14cfe353bc4e90211381d52043e7dc0d1cdc5
parent9a683bfb84464bbf051236c4e3c2710219cbf0d5 (diff)
Android: Use the application's class loader when loading Java classes.
Previously the system class loader was used, which meant only system Java classes where available. With this change it's no longer necessary to add a JNI_OnLoad() to get a handle to application specific classes. Change-Id: Ic8fe35b4e525bfeb1d317d5ba6b496e39bf9bb30 Reviewed-by: Yoann Lopes <yoann.lopes@digia.com>
-rw-r--r--src/corelib/kernel/qjni.cpp16
-rw-r--r--src/corelib/kernel/qjnihelpers.cpp20
-rw-r--r--src/corelib/kernel/qjnihelpers_p.h1
3 files changed, 33 insertions, 4 deletions
diff --git a/src/corelib/kernel/qjni.cpp b/src/corelib/kernel/qjni.cpp
index f26d4379d3..d1113e4eae 100644
--- a/src/corelib/kernel/qjni.cpp
+++ b/src/corelib/kernel/qjni.cpp
@@ -70,16 +70,24 @@ static jclass getCachedClass(JNIEnv *env, const char *className)
QString key = QLatin1String(className);
QHash<QString, jclass>::iterator it = cachedClasses->find(key);
if (it == cachedClasses->end()) {
- jclass c = env->FindClass(className);
+ QJNIObjectPrivate classLoader = QtAndroidPrivate::classLoader();
+ if (!classLoader.isValid())
+ return 0;
+
+ QJNIObjectPrivate stringName = QJNIObjectPrivate::fromString(QLatin1String(className));
+ QJNIObjectPrivate classObject = classLoader.callObjectMethod("loadClass",
+ "(Ljava/lang/String;)Ljava/lang/Class;",
+ stringName.object());
if (env->ExceptionCheck()) {
- c = 0;
#ifdef QT_DEBUG
env->ExceptionDescribe();
#endif // QT_DEBUG
env->ExceptionClear();
}
- if (c)
- clazz = static_cast<jclass>(env->NewGlobalRef(c));
+
+ if (classObject.isValid())
+ clazz = static_cast<jclass>(env->NewGlobalRef(classObject.object()));
+
cachedClasses->insert(key, clazz);
} else {
clazz = it.value();
diff --git a/src/corelib/kernel/qjnihelpers.cpp b/src/corelib/kernel/qjnihelpers.cpp
index a95194b66a..fbcd0606e6 100644
--- a/src/corelib/kernel/qjnihelpers.cpp
+++ b/src/corelib/kernel/qjnihelpers.cpp
@@ -45,6 +45,7 @@ QT_BEGIN_NAMESPACE
static JavaVM *g_javaVM = Q_NULLPTR;
static jobject g_jActivity = Q_NULLPTR;
+static jobject g_jClassLoader = Q_NULLPTR;
static inline bool exceptionCheck(JNIEnv *env)
{
@@ -79,6 +80,20 @@ jint QtAndroidPrivate::initJNI(JavaVM *vm, JNIEnv *env)
if (exceptionCheck(env))
return JNI_ERR;
+
+
+ jmethodID classLoaderMethodID = env->GetStaticMethodID(jQtNative,
+ "classLoader",
+ "()Ljava/lang/ClassLoader;");
+
+ if (exceptionCheck(env))
+ return JNI_ERR;
+
+ jobject classLoader = env->CallStaticObjectMethod(jQtNative, classLoaderMethodID);
+ if (exceptionCheck(env))
+ return JNI_ERR;
+
+ g_jClassLoader = env->NewGlobalRef(classLoader);
g_jActivity = env->NewGlobalRef(activity);
g_javaVM = vm;
@@ -96,4 +111,9 @@ JavaVM *QtAndroidPrivate::javaVM()
return g_javaVM;
}
+jobject QtAndroidPrivate::classLoader()
+{
+ return g_jClassLoader;
+}
+
QT_END_NAMESPACE
diff --git a/src/corelib/kernel/qjnihelpers_p.h b/src/corelib/kernel/qjnihelpers_p.h
index 8719ae044b..39059db215 100644
--- a/src/corelib/kernel/qjnihelpers_p.h
+++ b/src/corelib/kernel/qjnihelpers_p.h
@@ -63,6 +63,7 @@ namespace QtAndroidPrivate
Q_CORE_EXPORT jobject activity();
Q_CORE_EXPORT JavaVM *javaVM();
Q_CORE_EXPORT jint initJNI(JavaVM *vm, JNIEnv *env);
+ jobject classLoader();
}
QT_END_NAMESPACE