当前位置: 首页 > 知识库问答 >
问题:

在ubuntu上使用JNI时的java.lang.UnsatisfiedLinkError

邴宏大
2023-03-14

使用JNI时的java.lang.UnsatisfiedLinkError。

我的测试环境:

Ubuntu 12.04/64位
JDK 1.7
gcc(Ubuntu/Linaro 4.6.3-1Ubuntu5)

public class HelloJNI {
    static {
        //System.loadLibrary("libHelloJNI");
    }

    private native void sayHello() ;

    public static void main(String[] args){
        //System.getProperties().list(System.out);
        String lib_path = System.getProperty("java.library.path");
        System.out.println("java.library.path=" + lib_path);

        System.loadLibrary("libHelloJNI");

        HelloJNI myJNI = new HelloJNI();
        myJNI.sayHello();
    }
}
#include <stdio.h>
#include "HelloJNI.h"

JNIEXPORT void JNICALL Java_HelloJNI_sayHello(JNIEnv *env, jobject thisObj)
{
    puts("Hello Momo. This is C code.");
    return;
}
JNI_INC=-I"${JAVA_HOME}/include" -I"${JAVA_HOME}/include/linux"

JNI_LIB=libHelloJNI.so
JNI_OUT=$(JNI_LIB) HelloJNI.h HelloJNI.class
CFLAGS= $(JNI_INC) -fPIC -shared

all: $(JNI_OUT)

HelloJNI.h: HelloJNI.class
    javah -jni HelloJNI

$(JNI_LIB): HelloJNI.c HelloJNI.h
    gcc $(CFLAGS) -o $@  HelloJNI.c

HelloJNI.class: HelloJNI.java
    javac HelloJNI.java

run:
    java  HelloJNI
    #java -Djava.library.path=. HelloJNI

clean:
    rm $(JNI_OUT) 

已提取java_tool_options:-dfile.encoding=utf8 java.library.path=.:/home/mancook/cook/work/stsoftware/src/java/sttestjni/tutor01_hellojni:/usr/java/packages/lib/amd64:/usr/lib64:/lib64:/usr/lib64:/usr/lib
线程“main”中出现异常java.lang.unsatistiedlink错误:java.library.path中没有libHelloJNI
在java.lang.ClassLoader.LoadLibrary(ClassLoader.java:1886)
在>在java.lang.System.LoadLibrary(system.java:1088)
在hellojni.main(Hellojni.java:22)
make:***[run]错误1

我在网上搜索过这个问题,发现这是一个老问题。但是我找不到任何方法来解决我的问题!!希望有人能帮助我。提前道谢。

共有1个答案

谭裕
2023-03-14

在Makefile中需要-djava.library.path=.,并且需要用System.LoadLibrary(“hellojni”)加载库;-nolib前缀,no.so后缀。前缀和后缀由Java处理--想想看,Windows上的命名方案是不同的(愚蠢但事实)。并且要提防这样的陷阱:您的代码中有system.loadLibrary()两次,如果您只更改其中一次,它仍然会失败。我花了几分钟的时间

附注:我建议对makefile做一些修改。我将使用$(RM)而不是RM。不是文件的目标应声明为.phony。不引用自动变量的变量可以用:=而不是=赋值。我将使用单独的步骤从.o文件创建.so。我将使用模式规则来编译Java,如%.class:%.Java。我将使用模式规则来创建头文件,如%.h:%.class-i内容应该在cppflags中,而不是在cflags中,因为它是用于预处理器的。-shared然后应该进入ldflags等等...

以下是您的新生成文件:

CPPFLAGS:=-I"${JAVA_HOME}/include" -I"${JAVA_HOME}/include/linux"

JNI_LIB:=libHelloJNI.so
JNI_OUT:=$(JNI_LIB) HelloJNI.o HelloJNI.h HelloJNI.class
CFLAGS:=-fPIC
LDFLAGS:=-shared

.PHONY: all
all: $(JNI_OUT)

%.h: %.class
    javah -jni HelloJNI

$(JNI_LIB): HelloJNI.o
    $(LINK.o) $^ $(LOADLIBES) $(LDLIBS) -o $@

HelloJNI.o: HelloJNI.c HelloJNI.h

%.class: %.java
    javac HelloJNI.java

.PHONY: run
run:
    java -Djava.library.path=. HelloJNI

.PHONY: clean
clean:
    $(RM) $(JNI_OUT)
 类似资料:
  • 我正在阅读有关C中线程的教程并测试了以下代码: 我试图使用gcc和g编译此代码,但我总是遇到编译错误。 使用gcc-pthread thread_test.c: /tmp/ccmpQLyp。o: 在函数std::cout'thread_test.cpp: 你能帮忙吗?我必须做些什么才能让这段代码在Linux和Windows上运行吗?

  • java emmarun-jar helloworld.jar 我明白了: 线程“main”java.lang.noClassDeffounderror:emmarun中的异常由:java.lang.ClassNotFoundException:emmarun在java.net.urlClassLoader$1.run(urlClassLoader.java:217)在java.net.urlCl

  • 问题内容: 任何人都可以指导如何使用GDB调试器在Linux上调试JNI代码(如果可能,请提出其他选择)。 我已经安装了Gdb,但是没有得到如何使用它调试项目的信息。我是否还需要使用-g选项t debug .so文件来编译.cpp文件? 问题答案: 启动您的Java应用程序 使用top,ps,…查找pid 使用此pid启动gdb 附加程序代码 像往常一样使用gdb进行调试 这篇博客文章解释了整个过

  • 问题内容: 我正在使用Ubuntu 16.04,该版本随附Python 2.7和Python 3.5。我已经在上面安装了Python 3.6,并通过将符号3链接到python3.6 。 然后,我使用安装了。当我检查时,virtualenv已安装在适当的位置,因此当我尝试使用它创建virtualenv时,会抛出错误: 我该怎么办? 问题答案: 我们通常用来创建一个新的virtualenv(这是我们的

  • 我试着遵循这些说明:https://stackoverflow.com/a/40312117/21728基本上是这样做的: 但是当我执行任何网络操作时,我收到此错误: 我想这是合乎逻辑的,因为确实没有X11显示屏。 如何让Git凭证缓存在Windows上的Ubuntu(WSL)上工作?

  • 当我尝试在ubuntu上安装Yeoman时,我得到了以下错误。 编辑 尝试MortezaLSC的解决方案后-我得到以下错误