【问题标题】:Loading dynamic libraries using JNI and C++ with linux在 linux 中使用 JNI 和 C++ 加载动态库
【发布时间】:2013-02-25 21:26:24
【问题描述】:

最近我正在学习 JNI 来执行 C 代码。当然,我做了网络上的基本示例。现在我正在尝试加载一个可以进行动态库加载(dlopen)的 C 库。但我正在与错误作斗争。我发布了我的 Java 代码、C++ 代码和错误。

我的 Java 类

 /**
  *
  * @author glassfish
  */
 public class MediationJniWeb {

    public String library ;

    static {
       System.loadLibrary("-core-web");        
    }  

    /**
     *
     * @param library name of mediation core library [32]
     * @param method name of method to be executed [128]
     * @param parameters parameters of method [10240]
     *        [partype1,value1,...,valuen]...[partypen,value1,..,valuen]
     * @return
     */
     private native String execute();

     public static void main(String args[]) {
         //new MediationJniWeb().callToFunction(null, null, null) ;
         MediationJniWeb jniWeb = new MediationJniWeb();
         jniWeb.library = "libtest.so" ;

         System.out.println(jniWeb.execute());
     }
    }

我用

生成.class文件

javac MediationJniWeb

我生成 .h 文件

javah -jni MediationJniWeb

我的 MediationJniWeb.h 文件是

/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class MediationJniWeb */

#ifndef _Included_MediationJniWeb
#define _Included_MediationJniWeb
#ifdef __cplusplus
extern "C" {
#endif
/*
 * Class:     MediationJniWeb
 * Method:    execute
 * Signature: ()Ljava/lang/String;
 */
JNIEXPORT jstring JNICALL Java_MediationJniWeb_execute
  (JNIEnv *, jobject);

#ifdef __cplusplus
}
#endif
#endif

还有我的 MediationJniWEb.cpp 文件

/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
#include <dlfcn.h>
#include <iostream>

#include "MediationJniWeb.h"

using namespace std ;

typedef void (*test)(string);
/*
 * Class:     MediationJniWeb
 * Method:    execute
 * Signature: ()Ljava/lang/String;
 */
JNIEXPORT jstring JNICALL Java_MediationJniWeb_execute
  (JNIEnv * env, jobject obj){

        const char * str_library ;
        jfieldID fid_library ;
        jstring jstr_library ;
        jboolean isCopy ;

        jclass cls = env->GetObjectClass( obj) ; 
        fid_library  = env->GetFieldID( cls,"library", "Ljava/lang/String;");
        jstr_library = ( jstring )env->GetObjectField( obj,fid_library);
        str_library = env->GetStringUTFChars( jstr_library, &isCopy) ; 

        void* handle = dlopen(str_library, RTLD_NOW); // open libtest.so

        if ( 0 == handle ) {
        cout << "failed to load 'libtest.so'. " << dlerror () <<endl;
        exit(1);
        }

        test t = (test)dlsym(handle, "_Z8testfuncSs"); // run default method
        if ( 0 == t ) {
        cout << "failed to load 'testfunc()'." << endl;
        exit(1);
        }
        t("Hello, World!");
        dlclose(handle); 

        /*
        */
        return env->NewStringUTF( str_library); // I just return library name just for fun
    }

  }

我用编译

g++ -shared -fpic -I//include/ -I//include/linux/ MediationJniWeb.cpp -o lib-core-web.so MediationJniWeb.cpp -ldl

这会生成 lib-core-web.so 文件。然后我将它复制到 $HOME/lib 并配置

LD_LIBRARY_PATH=$HOME/lib

现在我创建了我的库 libtest.so,它将由 lib-core-web.so 执行

我为共享库 mylib.cpp 创建文件

#include <iostream>
#include <string>

using namespace std;

void testfunc(string s)
{
  cout << s << endl;
}

我编译这个将作为共享库使用

g++ -shared -fpic -o libtest.so mylib.cpp

此命令生成 libtest.so 文件.. 而且,我将其复制到 $HOME/lib

这就是我从 JNI 调用 C++ 库以加载动态库的全部工作。 当我执行 MediationJniWeb java 类时出现此错误

加载失败。 libtest.so:无法打开共享对象文件:没有这样的 文件或目录

我与 libtest.so 有什么关系?我必须把它放在哪里?

我想到只用正确的路径配置 LD_LIBRARY_PATH 变量,JVM 应该知道在哪里可以找到所有需要加载的库。

请帮助您的 cmets,让我知道我的错误在哪里。

提前致谢!

【问题讨论】:

  • 可能要考虑改用 JNA...这样就不需要您编写的大部分代码了。
  • JNA 听起来很有趣,但这样做的目的是我将加载我自己的一组 c 库(我们有一个使用许多 .so 文件的大型应用程序)并且可能会导致一些执行问题。顺便说一句,我想知道您是否有使用 Web 本地访问的经验。如果这有用或在部署时遇到一些问题或问题

标签: java c++ linux


【解决方案1】:

我做了一件简单的事

而不是

jniWeb.library = "libtest.so"

我声明要加载的库参数

jniWeb.library = "/home/myuser/lib/libtest.so"

它成功了!

【讨论】:

    猜你喜欢
    • 2020-02-27
    • 2014-03-04
    • 1970-01-01
    • 2014-06-18
    • 2012-12-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-10-31
    相关资源
    最近更新 更多