2

I need a way to load library inside a jar file without extracting it. Is there a way I can use a method like getClass().getResourceAsStream("xxx")

structure will be as follows:

myjar.jar
 - lib/
   - <somelib>.<libext>
 - <package>
   - Foo.class

Where the Foo.class will be the class that loads and connect to the native library and method should also work if the lib folder was inside the <package>

Android_Dev
  • 41
  • 1
  • 7

3 Answers3

0

No, there is no way to load library from inside of a jar file without extracting it first, you need to extract the library at least into tmp folder in order to be able to load it using eg:

System.load("path/to/libAbc.so")

It is not currently possible in java to load the library from memory or zip file. The method that loads the library is native void ClassLoader.NativeLibrary.load(String name), also the name of the library is used internally by the java.lang.ClassLoader to keep the track of loaded libraries, so currently you can't use anything different than a real file to be loaded as native library because it wouldn't fit the current mechanism.

Since the loading of the native library is done with the help of native code, the answer depends if there is a way to load the native library in a C code: dlopen from memory?

Theoretically it can be done, but bacause it is platform specific and have many aspects that needs to be considered and resolved it isn't implemented in Java and it isn't a standard and/or easy thing in C either.

Currently in java, there is no way to do it, this could change if someone will create such a native library that will do that, but for now I don't know any such library.

Krzysztof Cichocki
  • 6,294
  • 1
  • 16
  • 32
  • Should not be the case as it can read any file inside the jar and the lib is still a file and System.LoadLibrary() will still be reading the file in the path. So should there not be a way to send it the full content directly in memory and it reads from this memory?? – Android_Dev Aug 16 '17 at 12:14
  • @Android_Dev *Should not be the case as it can read any file inside the jar and the lib is still a file and System.LoadLibrary() will still be reading the file in the path. So should there not be a way to send it the full content directly in memory and it reads from this memory??* Why would you think that? Loading a *native library* is done by the operating system, not the JVM. – Andrew Henle Aug 16 '17 at 12:31
  • @AndrewHenle Yes I know it has to be loaded by operating system but, the operating system does not care about physical location of the code the pointers and registers to the code are stored in memory so if i can send everything straight to this point it will execute as normal (I'm assuming). – Android_Dev Aug 16 '17 at 12:35
  • Looking at the source code java stores pointer to the function and uses this to execute native tasks. `NativeLibrary#find(String)`. So there might be someway around. – Android_Dev Aug 16 '17 at 22:58
0

You can't do it without putting it somewhere (at least some temporary location).

You can take a look here:

https://github.com/mkowsiak/jnicookbook/tree/master/recipes/recipeNo031

This recipe gives you a template that will take your native library from jar, extract it, and load inside your Java code.

Have fun with JNI!

Oo.oO
  • 12,464
  • 3
  • 23
  • 45
0

Also sci-java native lib loader handles this (although it extracts it behind the scenes). You may want to try it: https://mvnrepository.com/artifact/org.scijava/native-lib-loader

Cristian Botiza
  • 419
  • 4
  • 9