зеркало из https://github.com/mozilla/pjs.git
[not part of build] Added pending exception support, to deal with problem of not being able to enter monitors with a pending exception in the JNIEnv.
This commit is contained in:
Родитель
0b905e50bf
Коммит
cab988a630
|
@ -152,6 +152,7 @@ static void netscape_oji_JNIThread_run(JNIEnv* env, jobject self)
|
|||
JavaMessage* msg = requests.getMessage();
|
||||
if (msg != NULL) {
|
||||
msg->execute(env);
|
||||
secureEnv->savePendingException(env);
|
||||
replies.putMessage(msg);
|
||||
replies.notify();
|
||||
} else {
|
||||
|
@ -354,7 +355,7 @@ CSecureEnv::CSecureEnv(MRJPlugin* plugin, JNIEnv* proxyEnv, JNIEnv* javaEnv)
|
|||
: SupportsMixin(this, sInterfaces, kInterfaceCount),
|
||||
mPlugin(plugin), mProxyEnv(proxyEnv), mJavaEnv(javaEnv),
|
||||
mSession(plugin->getSession()), mThreadManager(plugin->getThreadManager()),
|
||||
mIsRunning(NULL), mJavaQueue(NULL), mNativeQueue(NULL)
|
||||
mIsRunning(NULL), mJavaQueue(NULL), mNativeQueue(NULL), mPendingException(NULL)
|
||||
{
|
||||
// need to create the JNIThread for communicating with Java.
|
||||
if (mJavaEnv != NULL)
|
||||
|
@ -1451,16 +1452,18 @@ NS_IMETHODIMP CSecureEnv::ThrowNew(/*[in]*/ jclass clazz,
|
|||
|
||||
|
||||
class ExceptionOccurredMessage : public JavaMessage {
|
||||
CSecureEnv* secureEnv;
|
||||
jthrowable* result;
|
||||
public:
|
||||
ExceptionOccurredMessage(jthrowable* result)
|
||||
ExceptionOccurredMessage(CSecureEnv* secureEnv, jthrowable* result)
|
||||
{
|
||||
this->secureEnv = secureEnv;
|
||||
this->result = result;
|
||||
}
|
||||
|
||||
virtual void execute(JNIEnv* env)
|
||||
{
|
||||
*result = env->ExceptionOccurred();
|
||||
*result = secureEnv->getPendingException(env);
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -1470,7 +1473,7 @@ NS_IMETHODIMP CSecureEnv::ExceptionOccurred(/*[out]*/ jthrowable* result)
|
|||
return NS_ERROR_NULL_POINTER;
|
||||
|
||||
#if PROXY_JNI_CALLS
|
||||
ExceptionOccurredMessage msg(result);
|
||||
ExceptionOccurredMessage msg(this, result);
|
||||
sendMessageToJava(&msg);
|
||||
#else
|
||||
*result = mJavaEnv->ExceptionOccurred();
|
||||
|
@ -1497,14 +1500,20 @@ NS_IMETHODIMP CSecureEnv::ExceptionDescribe(void)
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
class ExceptionClearMessage : public JavaMessage {
|
||||
CSecureEnv* secureEnv;
|
||||
public:
|
||||
ExceptionClearMessage(CSecureEnv* secureEnv)
|
||||
{
|
||||
this->secureEnv = secureEnv;
|
||||
}
|
||||
virtual void execute(JNIEnv* env) { secureEnv->clearPendingException(env); }
|
||||
};
|
||||
|
||||
NS_IMETHODIMP CSecureEnv::ExceptionClear(void)
|
||||
{
|
||||
#if PROXY_JNI_CALLS
|
||||
class ExceptionClearMessage : public JavaMessage {
|
||||
public:
|
||||
virtual void execute(JNIEnv* env) { env->ExceptionClear(); }
|
||||
} msg;
|
||||
ExceptionClearMessage msg(this);
|
||||
sendMessageToJava(&msg);
|
||||
#else
|
||||
mJavaEnv->ExceptionClear();
|
||||
|
@ -2920,6 +2929,36 @@ void CSecureEnv::messageLoop(JNIEnv* env, JavaMessage* msg, JavaMessageQueue* se
|
|||
}
|
||||
}
|
||||
|
||||
void CSecureEnv::savePendingException(JNIEnv* env)
|
||||
{
|
||||
// first off, always restore the env to a known state.
|
||||
jthrowable pendingException = env->ExceptionOccurred();
|
||||
env->ExceptionClear();
|
||||
|
||||
if (mPendingException)
|
||||
env->DeleteGlobalRef(mPendingException);
|
||||
|
||||
if (pendingException) {
|
||||
mPendingException = (jthrowable) env->NewGlobalRef(pendingException);
|
||||
env->DeleteLocalRef(pendingException);
|
||||
}
|
||||
}
|
||||
|
||||
jthrowable CSecureEnv::getPendingException(JNIEnv* env)
|
||||
{
|
||||
if (mPendingException)
|
||||
return (jthrowable) env->NewLocalRef(mPendingException);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void CSecureEnv::clearPendingException(JNIEnv* env)
|
||||
{
|
||||
if (mPendingException) {
|
||||
env->DeleteGlobalRef(mPendingException);
|
||||
mPendingException = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
CSecureEnv* GetSecureJNI(JNIEnv* env, jobject thread)
|
||||
{
|
||||
CSecureEnv* secureJNI = NULL;
|
||||
|
|
|
@ -392,6 +392,10 @@ public:
|
|||
void sendMessageFromJava(JNIEnv* javaEnv, JavaMessage* msg, Boolean busyWaiting = false);
|
||||
void messageLoop(JNIEnv* env, JavaMessage* msgToSend, JavaMessageQueue* sendQueue, JavaMessageQueue* receiveQueue, Boolean busyWaiting = false);
|
||||
|
||||
void savePendingException(JNIEnv* env);
|
||||
jthrowable getPendingException(JNIEnv* env);
|
||||
void clearPendingException(JNIEnv* env);
|
||||
|
||||
protected:
|
||||
|
||||
MRJPlugin* mPlugin;
|
||||
|
@ -404,6 +408,8 @@ protected:
|
|||
JavaMessageQueue* mJavaQueue;
|
||||
JavaMessageQueue* mNativeQueue;
|
||||
|
||||
jthrowable mPendingException;
|
||||
|
||||
private:
|
||||
// support for SupportsMixin.
|
||||
static const InterfaceInfo sInterfaces[];
|
||||
|
|
Загрузка…
Ссылка в новой задаче