You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@nifi.apache.org by ph...@apache.org on 2019/03/05 19:39:53 UTC

[nifi-minifi-cpp] branch master updated: MINIFICPP-751 - RAII over JNI UTF strings

This is an automated email from the ASF dual-hosted git repository.

phrocker pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nifi-minifi-cpp.git


The following commit(s) were added to refs/heads/master by this push:
     new 384597e  MINIFICPP-751 - RAII over JNI UTF strings
384597e is described below

commit 384597e4670c72e9197dc051a4978c37958ba11e
Author: Arpad Boda <ab...@hortonworks.com>
AuthorDate: Mon Mar 4 17:21:28 2019 +0100

    MINIFICPP-751 - RAII over JNI UTF strings
    
    This closes #496.
    
    Signed-off-by: Marc Parisi <ph...@apache.org>
---
 extensions/jni/JNIUtil.h                 | 38 ++++++++++++++++++++++++++++++++
 extensions/jni/JavaException.h           |  5 ++---
 extensions/jni/jvm/JniFlowFile.cpp       |  5 +----
 extensions/jni/jvm/JniLogger.cpp         | 21 +++++-------------
 extensions/jni/jvm/JniProcessContext.cpp |  5 +----
 extensions/jni/jvm/JniProcessSession.cpp | 28 +++++------------------
 extensions/jni/jvm/NarClassLoader.h      | 15 +++----------
 7 files changed, 57 insertions(+), 60 deletions(-)

diff --git a/extensions/jni/JNIUtil.h b/extensions/jni/JNIUtil.h
new file mode 100644
index 0000000..788ff2a
--- /dev/null
+++ b/extensions/jni/JNIUtil.h
@@ -0,0 +1,38 @@
+/**
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef NIFI_MINIFI_CPP_JNIUTIL_H
+#define NIFI_MINIFI_CPP_JNIUTIL_H
+
+#include <string>
+#include <jni.h>
+
+static inline std::string JniStringToUTF(JNIEnv *env, const jstring &jstr) {
+  if(!jstr && !env) {
+    return "";
+  }
+  const char * c_str = env->GetStringUTFChars(jstr, NULL);
+  if(c_str == NULL) {
+    return "";
+  }
+  std::string str = c_str;
+  env->ReleaseStringUTFChars(jstr, c_str);
+  return str;
+}
+
+#endif //NIFI_MINIFI_CPP_JNIUTIL_H
diff --git a/extensions/jni/JavaException.h b/extensions/jni/JavaException.h
index 9fd3bd6..ec701b0 100644
--- a/extensions/jni/JavaException.h
+++ b/extensions/jni/JavaException.h
@@ -27,6 +27,7 @@
 #include "core/expect.h"
 #include <jni.h>
 #include "jvm/JavaDefs.h"
+#include "JNIUtil.h"
 
 namespace org {
 namespace apache {
@@ -70,10 +71,8 @@ static std::string getMessage(JNIEnv *env, jthrowable throwable) {
   }
   jstring message = (jstring) env->CallObjectMethod(throwable, getMessage);
   if (message) {
-    const char *mstr = env->GetStringUTFChars(message, NULL);
     // do whatever with mstr
-    std::string excp = mstr;
-    env->ReleaseStringUTFChars(message, mstr);
+    std::string excp = JniStringToUTF(env, message);
     env->DeleteLocalRef(message);
     env->DeleteLocalRef(clazz);
     return excp;
diff --git a/extensions/jni/jvm/JniFlowFile.cpp b/extensions/jni/jvm/JniFlowFile.cpp
index 84bf55b..ec34395 100644
--- a/extensions/jni/jvm/JniFlowFile.cpp
+++ b/extensions/jni/jvm/JniFlowFile.cpp
@@ -101,11 +101,8 @@ jstring Java_org_apache_nifi_processor_JniFlowFile_getAttribute(JNIEnv *env, job
 
   auto ff = ptr->get();
   THROW_IF_NULL(ff, env, NO_FF_OBJECT);
-  const char *kstr = env->GetStringUTFChars(key, 0);
   std::string value;
-  std::string keystr = kstr;
-  ff->getAttribute(keystr, value);
-  env->ReleaseStringUTFChars(key, kstr);
+  ff->getAttribute(JniStringToUTF(env, key), value);
   return env->NewStringUTF(value.c_str());
 }
 jlong Java_org_apache_nifi_processor_JniFlowFile_getSize(JNIEnv *env, jobject obj) {
diff --git a/extensions/jni/jvm/JniLogger.cpp b/extensions/jni/jvm/JniLogger.cpp
index 9cbc44d..1d696ff 100644
--- a/extensions/jni/jvm/JniLogger.cpp
+++ b/extensions/jni/jvm/JniLogger.cpp
@@ -34,6 +34,7 @@
 #include "JniFlowFile.h"
 #include "../JavaException.h"
 #include "core/logging/Logger.h"
+#include "../JNIUtil.h"
 
 #ifdef __cplusplus
 extern "C" {
@@ -64,42 +65,32 @@ void Java_org_apache_nifi_processor_JniLogger_warn(JNIEnv *env, jobject obj, jst
   minifi::jni::JniLogger *logger_ref = minifi::jni::JVMLoader::getPtr<minifi::jni::JniLogger>(env, obj);
   if (!logger_ref)
     return;
-  const char *msgStr = env->GetStringUTFChars(msg, 0);
-  logger_ref->logger_reference_->log_warn(msgStr);
-  env->ReleaseStringUTFChars(msg, msgStr);
+  logger_ref->logger_reference_->log_warn(JniStringToUTF(env, msg).c_str());
 }
 
 void Java_org_apache_nifi_processor_JniLogger_error(JNIEnv *env, jobject obj, jstring msg) {
   minifi::jni::JniLogger *logger_ref = minifi::jni::JVMLoader::getPtr<minifi::jni::JniLogger>(env, obj);
   if (!logger_ref)
     return;
-  const char *msgStr = env->GetStringUTFChars(msg, 0);
-  logger_ref->logger_reference_->log_error(msgStr);
-  env->ReleaseStringUTFChars(msg, msgStr);
+  logger_ref->logger_reference_->log_error(JniStringToUTF(env, msg).c_str());
 }
 void Java_org_apache_nifi_processor_JniLogger_info(JNIEnv *env, jobject obj, jstring msg) {
   minifi::jni::JniLogger *logger_ref = minifi::jni::JVMLoader::getPtr<minifi::jni::JniLogger>(env, obj);
   if (!logger_ref)
     return;
-  const char *msgStr = env->GetStringUTFChars(msg, 0);
-  logger_ref->logger_reference_->log_info(msgStr);
-  env->ReleaseStringUTFChars(msg, msgStr);
+  logger_ref->logger_reference_->log_info(JniStringToUTF(env, msg).c_str());
 }
 void Java_org_apache_nifi_processor_JniLogger_debug(JNIEnv *env, jobject obj, jstring msg) {
   minifi::jni::JniLogger *logger_ref = minifi::jni::JVMLoader::getPtr<minifi::jni::JniLogger>(env, obj);
   if (!logger_ref)
     return;
-  const char *msgStr = env->GetStringUTFChars(msg, 0);
-  logger_ref->logger_reference_->log_debug(msgStr);
-  env->ReleaseStringUTFChars(msg, msgStr);
+  logger_ref->logger_reference_->log_debug(JniStringToUTF(env, msg).c_str());
 }
 void Java_org_apache_nifi_processor_JniLogger_trace(JNIEnv *env, jobject obj, jstring msg) {
   minifi::jni::JniLogger *logger_ref = minifi::jni::JVMLoader::getPtr<minifi::jni::JniLogger>(env, obj);
   if (!logger_ref)
     return;
-  const char *msgStr = env->GetStringUTFChars(msg, 0);
-  logger_ref->logger_reference_->log_trace(msgStr);
-  env->ReleaseStringUTFChars(msg, msgStr);
+  logger_ref->logger_reference_->log_trace(JniStringToUTF(env, msg).c_str());
 }
 
 #ifdef __cplusplus
diff --git a/extensions/jni/jvm/JniProcessContext.cpp b/extensions/jni/jvm/JniProcessContext.cpp
index bd87661..288e1b5 100644
--- a/extensions/jni/jvm/JniProcessContext.cpp
+++ b/extensions/jni/jvm/JniProcessContext.cpp
@@ -40,16 +40,13 @@ jstring Java_org_apache_nifi_processor_JniProcessContext_getPropertyValue(JNIEnv
   if (context == nullptr || context->context_ == nullptr) {
     return nullptr;
   }
-  const char *kstr = env->GetStringUTFChars(propertyName, 0);
-  std::string keystr = kstr;
+  std::string keystr = JniStringToUTF(env, propertyName);
   if (!context->context_->getProperty(keystr, value)) {
     if (!context->context_->getDynamicProperty(keystr, value)) {
-      env->ReleaseStringUTFChars(propertyName, kstr);
       return nullptr;
     }
   }
 
-  env->ReleaseStringUTFChars(propertyName, kstr);
   return env->NewStringUTF(value.c_str());
 }
 
diff --git a/extensions/jni/jvm/JniProcessSession.cpp b/extensions/jni/jvm/JniProcessSession.cpp
index be25dd2..9fd24f9 100644
--- a/extensions/jni/jvm/JniProcessSession.cpp
+++ b/extensions/jni/jvm/JniProcessSession.cpp
@@ -221,21 +221,14 @@ jobject Java_org_apache_nifi_processor_JniProcessSession_putAttribute(JNIEnv *en
     return nullptr;
   }
   THROW_IF_NULL(ff, env, NO_FF_OBJECT);
-  minifi::jni::JniSession *session = minifi::jni::JVMLoader::getPtr<minifi::jni::JniSession>(env, obj);
   minifi::jni::JniFlowFile *ptr = minifi::jni::JVMLoader::getInstance()->getReference<minifi::jni::JniFlowFile>(env, ff);
 
   if (ff == nullptr || key == nullptr || value == nullptr) {
     return nullptr;
   }
 
-  const char *kstr = env->GetStringUTFChars(key, 0);
-  const char *vstr = env->GetStringUTFChars(value, 0);
-  std::string valuestr = vstr;
-  std::string keystr = kstr;
+  ptr->get()->addAttribute(JniStringToUTF(env, key), JniStringToUTF(env, value));
 
-  ptr->get()->addAttribute(keystr, valuestr);
-  env->ReleaseStringUTFChars(key, kstr);
-  env->ReleaseStringUTFChars(value, vstr);
   return ff;
 
 }
@@ -247,11 +240,8 @@ void Java_org_apache_nifi_processor_JniProcessSession_transfer(JNIEnv *env, jobj
   THROW_IF_NULL(ff, env, NO_FF_OBJECT);
   minifi::jni::JniSession *session = minifi::jni::JVMLoader::getPtr<minifi::jni::JniSession>(env, obj);
   minifi::jni::JniFlowFile *ptr = minifi::jni::JVMLoader::getInstance()->getReference<minifi::jni::JniFlowFile>(env, ff);
-  const char *relstr = env->GetStringUTFChars(relationship, 0);
-  std::string relString = relstr;
-  core::Relationship success(relString, "description");
-  session->getSession()->transfer(ptr->get(), success);
-  env->ReleaseStringUTFChars(relationship, relstr);
+  core::Relationship rel(JniStringToUTF(env, relationship), "description");
+  session->getSession()->transfer(ptr->get(), rel);
 }
 
 jstring Java_org_apache_nifi_processor_JniProcessSession_getPropertyValue(JNIEnv *env, jobject obj, jstring propertyName) {
@@ -260,12 +250,10 @@ jstring Java_org_apache_nifi_processor_JniProcessSession_getPropertyValue(JNIEnv
     return env->NewStringUTF(value.c_str());
   }
   core::ProcessContext *context = minifi::jni::JVMLoader::getPtr<core::ProcessContext>(env, obj);
-  const char *kstr = env->GetStringUTFChars(propertyName, 0);
-  std::string keystr = kstr;
+  std::string keystr = JniStringToUTF(env, propertyName);
   if (!context->getProperty(keystr, value)) {
     context->getDynamicProperty(keystr, value);
-  }
-  env->ReleaseStringUTFChars(propertyName, kstr);
+  };
   return env->NewStringUTF(value.c_str());
 }
 
@@ -401,14 +389,10 @@ jobject Java_org_apache_nifi_processor_JniProcessSession_removeAttribute(JNIEnv
     return ff;
   }
   THROW_IF_NULL(ff, env, NO_FF_OBJECT);
-  minifi::jni::JniSession *session = minifi::jni::JVMLoader::getPtr<minifi::jni::JniSession>(env, obj);
   minifi::jni::JniFlowFile *ptr = minifi::jni::JVMLoader::getInstance()->getReference<minifi::jni::JniFlowFile>(env, ff);
 
   if (ptr->get()) {
-    const char *attrStr = env->GetStringUTFChars(attr, 0);
-    std::string attribute = attrStr;
-    ptr->get()->removeAttribute(attribute);
-    env->ReleaseStringUTFChars(attr, attrStr);
+    ptr->get()->removeAttribute(JniStringToUTF(env, attr));
   }
   return ff;
 }
diff --git a/extensions/jni/jvm/NarClassLoader.h b/extensions/jni/jvm/NarClassLoader.h
index bd79ddf..223caed 100644
--- a/extensions/jni/jvm/NarClassLoader.h
+++ b/extensions/jni/jvm/NarClassLoader.h
@@ -96,10 +96,7 @@ class NarClassLoader {
       ThrowIf(env);
 
       if (obj) {
-        const char *str = env->GetStringUTFChars(obj, 0);
-
-        methodName = str;
-        env->ReleaseStringUTFChars(obj, str);
+        methodName = JniStringToUTF(env, obj);
       }
     }
     {
@@ -117,9 +114,7 @@ class NarClassLoader {
       ThrowIf(env);
 
       if (obj) {
-        const char *str = env->GetStringUTFChars(obj, 0);
-        signature = str;
-        env->ReleaseStringUTFChars(obj, str);
+        signature = JniStringToUTF(env, obj);
       }
     }
 
@@ -376,11 +371,7 @@ class NarClassLoader {
     ThrowIf(env);
     if (id == nullptr)
       return "";
-    auto id_chars = env->GetStringUTFChars(id, 0);
-
-    std::string artifact = id_chars;
-    env->ReleaseStringUTFChars(id, id_chars);
-    return artifact;
+    return JniStringToUTF(env, id);
   }
 
   std::string getArtifact(jclass bundle_coordinate, JNIEnv *env, jobject coord) {