Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code

Unified Diff: libadblockplus-android/jni/JniFileSystem.cpp

Issue 29424615: Issue 4231 - Fix unstable FilterEngineTest.testSetRemoveFilterChangeCallback (Closed)
Patch Set: now using smart_ptr, changed impl for reading file as string, minor changes Created May 22, 2017, 1:03 p.m.
Use n/p to move between diff chunks; N/P to move between comments.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: libadblockplus-android/jni/JniFileSystem.cpp
diff --git a/libadblockplus-android/jni/JniFileSystem.cpp b/libadblockplus-android/jni/JniFileSystem.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..0055f03cce9bc373e2fe2d8f490032c513aaf9a3
--- /dev/null
+++ b/libadblockplus-android/jni/JniFileSystem.cpp
@@ -0,0 +1,195 @@
+/*
+ * This file is part of Adblock Plus <https://adblockplus.org/>,
+ * Copyright (C) 2006-2017 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
+ * published by the Free Software Foundation.
+ *
+ * Adblock Plus is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Adblock Plus. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "JniCallbacks.h"
+#include "AdblockPlus/FileSystem.h"
+#include "Utils.h"
+#include <sstream>
+
+// precached in JNI_OnLoad and released in JNI_OnUnload
+JniGlobalReference<jclass>* statResultClass;
+jmethodID existsMethod;
+jmethodID isDirectoryMethod;
+jmethodID isFileMethod;
+jmethodID getLastModifiedMethod;
+
+void JniFileSystem_OnLoad(JavaVM* vm, JNIEnv* env, void* reserved)
+{
+ statResultClass = new JniGlobalReference<jclass>(env, env->FindClass(PKG("FileSystem$StatResult")));
+ existsMethod = env->GetMethodID(statResultClass->Get(), "exists", "()Z");
+ isDirectoryMethod = env->GetMethodID(statResultClass->Get(), "isDirectory", "()Z");
+ isFileMethod = env->GetMethodID(statResultClass->Get(), "isFile", "()Z");
+ getLastModifiedMethod = env->GetMethodID(statResultClass->Get(), "getLastModified", "()J");
+}
+
+void JniFileSystem_OnUnload(JavaVM* vm, JNIEnv* env, void* reserved)
+{
+ if (statResultClass)
+ {
+ delete statResultClass;
+ statResultClass = NULL;
+ }
+}
+
+static jlong JNICALL JniCtor(JNIEnv* env, jclass clazz, jobject callbackObject)
+{
+ try
+ {
+ return JniPtrToLong(new AdblockPlus::FileSystemPtr(new JniFileSystemCallback(env, callbackObject)));
+ }
+ CATCH_THROW_AND_RETURN(env, 0)
+}
+
+static void JNICALL JniDtor(JNIEnv* env, jclass clazz, jlong ptr)
+{
+ delete JniLongToTypePtr<AdblockPlus::FileSystemPtr>(ptr);
+}
+
+JniFileSystemCallback::JniFileSystemCallback(JNIEnv* env, jobject callbackObject)
+ : JniCallbackBase(env, callbackObject)
+{
+}
+
+std::shared_ptr<std::istream> JniFileSystemCallback::Read(const std::string& path) const
+{
+ JNIEnvAcquire env(GetJavaVM());
+
+ jmethodID method = env->GetMethodID(
+ *JniLocalReference<jclass>(*env, env->GetObjectClass(GetCallbackObject())),
+ "read",
+ "(Ljava/lang/String;)Ljava/lang/String;");
+
+ JniLocalReference<jstring> jPath(*env, env->NewStringUTF(path.c_str()));
+ jstring jData = (jstring)env->CallObjectMethod(GetCallbackObject(), method, *jPath);
+ CheckAndLogJavaException(*env);
+
+ if (!jData)
+ return NULL;
+
+ std::string cData = JniJavaToStdString(*env, jData);
+ std::shared_ptr<std::istream> cSharedStream(new std::istringstream(cData));
+ return cSharedStream;
+}
+
+void JniFileSystemCallback::Write(const std::string& path, std::shared_ptr<std::istream> data)
+{
+ JNIEnvAcquire env(GetJavaVM());
+
+ jmethodID method = env->GetMethodID(
+ *JniLocalReference<jclass>(*env, env->GetObjectClass(GetCallbackObject())),
+ "write",
+ "(Ljava/lang/String;Ljava/lang/String;)V");
+
+ JniLocalReference<jstring> jPath(*env, env->NewStringUTF(path.c_str()));
+
+ // read all the data from the stream into buffer (no appropriate way to pass streams over JNI)
+ std::string cData = AdblockPlus::Utils::Slurp(*data.get());
+ JniLocalReference<jstring> jData(*env, env->NewStringUTF(cData.c_str()));
+
+ env->CallVoidMethod(GetCallbackObject(), method, *jPath, *jData);
+ CheckAndLogJavaException(*env);
+}
+
+void JniFileSystemCallback::Move(const std::string& fromPath, const std::string& toPath)
+{
+ JNIEnvAcquire env(GetJavaVM());
+
+ jmethodID method = env->GetMethodID(
+ *JniLocalReference<jclass>(*env, env->GetObjectClass(GetCallbackObject())),
+ "move",
+ "(Ljava/lang/String;Ljava/lang/String;)V");
+
+ JniLocalReference<jstring> jFromPath(*env, env->NewStringUTF(fromPath.c_str()));
+ JniLocalReference<jstring> jToPath(*env, env->NewStringUTF(toPath.c_str()));
+
+ env->CallVoidMethod(GetCallbackObject(), method, *jFromPath, *jToPath);
+ CheckAndLogJavaException(*env);
+}
+
+void JniFileSystemCallback::Remove(const std::string& path)
+{
+ JNIEnvAcquire env(GetJavaVM());
+
+ jmethodID method = env->GetMethodID(
+ *JniLocalReference<jclass>(*env, env->GetObjectClass(GetCallbackObject())),
+ "remove",
+ "(Ljava/lang/String;)V");
+
+ JniLocalReference<jstring> jPath(*env, env->NewStringUTF(path.c_str()));
+
+ env->CallVoidMethod(GetCallbackObject(), method, *jPath);
+ CheckAndLogJavaException(*env);
+}
+
+AdblockPlus::FileSystem::StatResult JniFileSystemCallback::Stat(const std::string& path) const
+{
+ JNIEnvAcquire env(GetJavaVM());
+
+ jmethodID method = env->GetMethodID(
+ *JniLocalReference<jclass>(*env, env->GetObjectClass(GetCallbackObject())),
+ "stat",
+ "(Ljava/lang/String;)" TYP("FileSystem$StatResult"));
+
+ JniLocalReference<jstring> jPath(*env, env->NewStringUTF(path.c_str()));
+
+ jobject jStatResult = env->CallObjectMethod(GetCallbackObject(), method, *jPath);
+ CheckAndLogJavaException(*env);
+
+ AdblockPlus::FileSystem::StatResult statResult;
+
+ statResult.exists = env->CallBooleanMethod(jStatResult, existsMethod) ? JNI_TRUE : JNI_FALSE;
+ CheckAndLogJavaException(*env);
+
+ statResult.isDirectory = env->CallBooleanMethod(jStatResult, isDirectoryMethod) ? JNI_TRUE : JNI_FALSE;
+ CheckAndLogJavaException(*env);
+
+ statResult.isFile = env->CallBooleanMethod(jStatResult, isFileMethod) ? JNI_TRUE : JNI_FALSE;
+ CheckAndLogJavaException(*env);
+
+ statResult.lastModified = env->CallLongMethod(jStatResult, getLastModifiedMethod);
+ CheckAndLogJavaException(*env);
+
+ return statResult;
+}
+
+std::string JniFileSystemCallback::Resolve(const std::string& path) const
+{
+ JNIEnvAcquire env(GetJavaVM());
+
+ jmethodID method = env->GetMethodID(
+ *JniLocalReference<jclass>(*env, env->GetObjectClass(GetCallbackObject())),
+ "resolve",
+ "(Ljava/lang/String;)Ljava/lang/String;");
+
+ JniLocalReference<jstring> jPath(*env, env->NewStringUTF(path.c_str()));
+
+ jstring jRet = (jstring)env->CallObjectMethod(GetCallbackObject(), method, *jPath);
+ CheckAndLogJavaException(*env);
+
+ return JniJavaToStdString(*env, jRet);
+}
+
+static JNINativeMethod methods[] =
+{
+ { (char*)"ctor", (char*)"(Ljava/lang/Object;)J", (void*)JniCtor },
+ { (char*)"dtor", (char*)"(J)V", (void*)JniDtor }
+};
+
+extern "C" JNIEXPORT void JNICALL Java_org_adblockplus_libadblockplus_FileSystem_registerNatives(JNIEnv *env, jclass clazz)
+{
+ env->RegisterNatives(clazz, methods, sizeof(methods) / sizeof(methods[0]));
+}

Powered by Google App Engine
This is Rietveld