简体   繁体   中英

JNI with static library: unsatisfied link error

I've built a static library with g++:

g++-5 main.cpp -fPIC -Wall -std=c++11 -lboost_system ......

Now I want to call its methods via JNI:

public static void main(String[] args) {
    System.load("/Users/XXX/example/libjnidb4java.a");
    JNIDB db = new JNIDB();
    db.createTable("Name", "Dir");
  }

Turns out there's a UnsatisfiedLinkError Exception:

Exception in thread "main" java.lang.UnsatisfiedLinkError: /Users/XXX/example/libjnidb4java.a: dlopen(/Users/XXX/example/libjnidb4java.a, 1): no suitable image found.  Did find:
    /Users/XXX/example/libjnidb4java.a: unknown file type, first eight bytes: 0x21 0x3C 0x61 0x72 0x63 0x68 0x3E 0x0A
    at java.lang.ClassLoader$NativeLibrary.load(Native Method)
    at java.lang.ClassLoader.loadLibrary0(ClassLoader.java:1937)
    at java.lang.ClassLoader.loadLibrary(ClassLoader.java:1822)
    at java.lang.Runtime.load0(Runtime.java:809)
    at java.lang.System.load(System.java:1086)

NOTE

I tried with dynamic library, it works fine, but in my case, I need it to be static library. I create this static library via ar -r libjnidb4java.a a.out .

And I found Java 8 has already supports statically linked library here . Like the docs say, I created a method :

jint JNI_OnLoad_xxxdb4java(JavaVM *vm, void *reserved) { return JNI_VERSION_1_8; }

You cannot dynamically load a static library. You can only dynamically load a shared library.

The JNI docs you refer to talk about using JNI with static libraries, but that assumes that you've statically linked a library into the JVM. So if you really must use a static library then you're going to have to rebuild your own JVM which sounds like an unenviable experience.

It's not clear to me why there's a difference for you between using a static library and a shared library (you are still trying to dynamically load it, after all, which screams dynamic library to me) but I would try to overcome that limitation first.

If you want to create a single installable unit for your users, then what you want is to create a single shared library of your own. Your library should then statically link its dependencies so that they are included in your library. You can then use loadLibrary on that single unit without worrying about dependencies being installed.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM