| Index: jni/Utils.h | 
| diff --git a/jni/Utils.h b/jni/Utils.h | 
| index 92231d78b0d137afb1e4f671679cb2cdc4e349db..dd3d600dee7e0e77e54029c020b563354d06e641 100644 | 
| --- a/jni/Utils.h | 
| +++ b/jni/Utils.h | 
| @@ -1,6 +1,6 @@ | 
| /* | 
| * This file is part of Adblock Plus <http://adblockplus.org/>, | 
| - * Copyright (C) 2006-2014 Eyeo GmbH | 
| + * Copyright (C) 2006-2013 Eyeo GmbH | 
| * | 
| * Adblock Plus is free software: you can redistribute it and/or modify | 
| * it under the terms of the GNU General Public License version 3 as | 
| @@ -21,6 +21,190 @@ | 
| #include <string> | 
| #include <algorithm> | 
| #include <jni.h> | 
| +#include <stdexcept> | 
| + | 
| +#include <AdblockPlus.h> | 
| +#include <AdblockPlus/tr1_memory.h> | 
| + | 
| +#include "v8/v8stdint.h" | 
| + | 
| +#define PKG(x) "org/adblockplus/android/api/" x | 
| +#define TYP(x) "L" PKG(x) ";" | 
| + | 
| +#define ABP_JNI_VERSION JNI_VERSION_1_6 | 
| + | 
| +namespace AdblockPlus | 
| +{ | 
| +namespace Android | 
| +{ | 
| + | 
| +void JniThrowException(JNIEnv* env, const std::string& message); | 
| + | 
| +void JniThrowException(JNIEnv* env, const std::exception& e); | 
| + | 
| +void JniThrowException(JNIEnv* env); | 
| + | 
| +class JNIEnvAcquire | 
| +{ | 
| +public: | 
| + JNIEnvAcquire(JavaVM* javaVM) : | 
| + m_JavaVM(javaVM), m_JNIEnv(0), m_AttachStatus(0) | 
| + { | 
| + m_AttachStatus = javaVM->GetEnv((void **)&m_JNIEnv, ABP_JNI_VERSION); | 
| + if (m_AttachStatus == JNI_EDETACHED) | 
| + { | 
| + if (javaVM->AttachCurrentThread(&m_JNIEnv, 0)) | 
| + { | 
| + // This one is FATAL, we can't recover from this (because without a JVM we're dead), so | 
| + // throwing a runtime_exception in a ctor can be tolerated here IMHO | 
| + throw std::runtime_error("Failed to get JNI environment"); | 
| + } | 
| + } | 
| + } | 
| + | 
| + ~JNIEnvAcquire() | 
| + { | 
| + if (m_AttachStatus == JNI_EDETACHED) | 
| + { | 
| + m_JavaVM->DetachCurrentThread(); | 
| + } | 
| + } | 
| + | 
| + inline JNIEnv* operator*() | 
| + { | 
| + return m_JNIEnv; | 
| + } | 
| + | 
| + inline JNIEnv* operator->() | 
| + { | 
| + return m_JNIEnv; | 
| + } | 
| + | 
| +private: | 
| + JavaVM* m_JavaVM; | 
| + JNIEnv* m_JNIEnv; | 
| + int m_AttachStatus; | 
| +}; | 
| + | 
| +template<typename T> | 
| +class JniGlobalReference | 
| +{ | 
| +public: | 
| + JniGlobalReference(JNIEnv* env, T reference) | 
| + { | 
| + env->GetJavaVM(&m_JavaVM); | 
| + m_Reference = static_cast<T>(env->NewGlobalRef(static_cast<jobject>(reference))); | 
| + } | 
| + | 
| + ~JniGlobalReference() | 
| + { | 
| + JNIEnvAcquire env(m_JavaVM); | 
| + | 
| + env->DeleteGlobalRef(static_cast<jobject>(m_Reference)); | 
| + } | 
| + | 
| + JniGlobalReference(const JniGlobalReference& other); | 
| + JniGlobalReference& operator=(const JniGlobalReference& other); | 
| + | 
| + inline T get() | 
| + { | 
| + return m_Reference; | 
| + } | 
| + | 
| + typedef std::tr1::shared_ptr<JniGlobalReference<T> > PTR; | 
| 
 
Felix Dahlke
2014/03/28 08:29:00
Looks like a macro this way, should be "Ptr" IMO.
 
 | 
| + | 
| +private: | 
| + T m_Reference; | 
| + JavaVM* m_JavaVM; | 
| +}; | 
| + | 
| +inline void* JniLong2Ptr(jlong value) | 
| +{ | 
| + return reinterpret_cast<void*>((size_t)value); | 
| +} | 
| + | 
| +inline jlong JniPtr2Long(void* ptr) | 
| +{ | 
| + return (jlong)reinterpret_cast<size_t>(ptr); | 
| +} | 
| + | 
| +// TODO(rje): It's feeling a bit dirty casting to shared_ptr<T: JsValue> directly, so maybe | 
| 
 
Felix Dahlke
2014/03/28 08:29:00
I'd ditch the (rje) part - it's apparent from hg l
 
 | 
| +// implement a special cast functions that first reinterpret_casts to shared_ptr<JsValue> and then | 
| +// dynamic_casts to shared_ptr<T: JsValue> ... also as the same inheritance is mirrored on the Java | 
| +// side (and Java will throw a class cast exception on error) this shouldn't be an issue (TM) | 
| +template<typename T> | 
| +inline T* JniLong2TypePtr(jlong value) | 
| +{ | 
| + return reinterpret_cast<T*>((size_t)value); | 
| +} | 
| + | 
| +jobject NewJniArrayList(JNIEnv* env); | 
| + | 
| +std::string JniJava2StdString(JNIEnv* env, jstring str); | 
| + | 
| +void JniAddObjectToList(JNIEnv* env, jobject list, jobject value); | 
| + | 
| +inline std::string JniGetStringField(JNIEnv* env, jclass clazz, jobject jObj, const char* name) | 
| +{ | 
| + return AdblockPlus::Android::JniJava2StdString(env, | 
| + reinterpret_cast<jstring>(env->GetObjectField(jObj, env->GetFieldID(clazz, name, "Ljava/lang/String;")))); | 
| +} | 
| + | 
| +inline bool JniGetBooleanField(JNIEnv* env, jclass clazz, jobject jObj, const char* name) | 
| +{ | 
| + return env->GetBooleanField(jObj, env->GetFieldID(clazz, name, "Z")) == JNI_TRUE; | 
| +} | 
| + | 
| +inline int32_t JniGetIntField(JNIEnv* env, jclass clazz, jobject jObj, const char* name) | 
| +{ | 
| + return (int32_t)env->GetBooleanField(jObj, env->GetFieldID(clazz, name, "I")); | 
| +} | 
| + | 
| +inline int64_t JniGetLongField(JNIEnv* env, jclass clazz, jobject jObj, const char* name) | 
| +{ | 
| + return (int64_t)env->GetBooleanField(jObj, env->GetFieldID(clazz, name, "J")); | 
| +} | 
| + | 
| +inline jobject NewJniFilter(JNIEnv* env, const AdblockPlus::FilterPtr& filter) | 
| +{ | 
| + jclass clazz = env->FindClass(PKG("Filter")); | 
| + jmethodID method = env->GetMethodID(clazz, "<init>", "(J)V"); | 
| + return env->NewObject(clazz, method, JniPtr2Long(new AdblockPlus::FilterPtr(filter))); | 
| +} | 
| + | 
| +inline jobject NewJniSubscription(JNIEnv* env, const AdblockPlus::SubscriptionPtr& subscription) | 
| +{ | 
| + jclass clazz = env->FindClass(PKG("Subscription")); | 
| + jmethodID method = env->GetMethodID(clazz, "<init>", "(J)V"); | 
| + return env->NewObject(clazz, method, JniPtr2Long(new AdblockPlus::SubscriptionPtr(subscription))); | 
| +} | 
| + | 
| +} // namespace Android | 
| +} // namespace AdblockPlus | 
| + | 
| +#define TRY try | 
| + | 
| +#define CATCH_AND_THROW(jEnv) \ | 
| + catch (const std::exception& except) \ | 
| + { \ | 
| + AdblockPlus::Android::JniThrowException(jEnv, except); \ | 
| + } \ | 
| + catch (...) \ | 
| + { \ | 
| + AdblockPlus::Android::JniThrowException(jEnv); \ | 
| + } | 
| + | 
| +#define CATCH_THROW_AND_RETURN(jEnv, retVal) \ | 
| + catch (const std::exception& except) \ | 
| + { \ | 
| + AdblockPlus::Android::JniThrowException(jEnv, except); \ | 
| + return retVal; \ | 
| + } \ | 
| + catch (...) \ | 
| + { \ | 
| + AdblockPlus::Android::JniThrowException(jEnv); \ | 
| + return retVal; \ | 
| + } | 
| const std::string GetString(JNIEnv *pEnv, jstring str); |