-
Notifications
You must be signed in to change notification settings - Fork 143
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Package Themis JNI library in DEB and RPM #553
Conversation
Introduce two new Makefile targets to install and uninstall Themis JNI library: themis_jni_{install,uninstall} The library is installed to $(jnidir) which is set to $(libdir) by default, but can be overriden. This is because Java is not required to look into standard system directories for JNI libraries and may have a different opinion about that. Note that libthemis_jni does not have ABI suffix, does not introduce development symbolic links, and does not define import libraries like Soter and Themis libraries do. This is because it is not meant to be used by linkers, only dynamically loaded by JVM. Therefore we can simply name it "libthemis_jni.so" and that's all: it's going to be loaded by path anyway, its SONAME does not matter. Also note that on macOS we invoke install_name_tool only during installation, not during build. This is in-line with other libraries and is the correct behavior (so that we do not have to rebuild the library before installing it into a different place).
Add a separate package called "libthemis-jni" with Themis JNI library used by JavaThemis wrapper. It depends on Themis Core library against which it is linked. Since we maintain backwards compatibility it should be possible to upgrade Themis Core independently and we allow later versions to satisfy the dependency. Debian Java policy prescribes that JNI libraries should be placed into a "jni" subdirectory in the default library directory. Since we support multilib that's something like /usr/lib/x86_64-linux-gnu/jni for x86_64 architecture. OpenJDK from Debian repositories has this path in its java.library.path list. CentOS conventions are to put JNI libraries right into the normal path like /usr/lib64. That's what we'll do when packaging RPMs.
Let's check Java library search paths and print out a warning if JNI library is being installed to a locations that's probably unreachable by default. Java installations are not required to look into system library directories. While normally OpenJDK and Oracle JDK installations do look into some directory in the /usr hierarchy, *none* of the systems that we support looks into "/usr/local/lib" where we install by default when compiling from source. This is unfortunate, but we should not decide for the user how they should be configuring their system when building from source, and we should not interfere with system package manager either. For Linux we provide packages that install JNI library into /usr subdirectories expected by Java. This is the preferred way to install Themis Core on Linux. Users that build from source will have to adjust JNI library location manually after installation. Unfortunately, on macOS Homebrew is not able to write to any of the Oracle's Java default paths except for the one in user's home directory: $HOME/Library/Java/Extensions /Library/Java/Extensions - requires root acccess /Network/Library/Java/Extensions - protected by SIP /System/Library/Java/Extensions - protected by SIP /usr/lib/java - protected by SIP $PWD Installing into $HOME or the current directory is not really an option for Homebrew. Thus on macOS we are most likely installing the library into a directory that's not reachable by default. Homebrew package should be adjusted to print out a relevant message to the user.
@$(PRINT_OK_) | ||
@java_library_path=$$(\ | ||
java -XshowSettings:properties -version 2>&1 \ | ||
| sed -E 's/^ +[^=]+ =/_&/' \ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
black magic happening here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well, if you'd like it can be replaced with the following Java code:
import java.io.File;
public final class Main {
public static void main(String[] args) {
String rawPath = System.getProperty("java.library.path");
String[] paths = rawPath.split(File.pathSeparator);
for (String path : paths) {
System.out.println(path);
}
}
}
Just need to compile and run it. Or we can bundle a precompiled *.jar.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
thank you for explanation, my skills of understanding regex "on the fly" are not perfect
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
lgtm
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Great, thanks!
Let’s provide proper packaging for the JNI library on Linux.
Introduce two new Makefile targets to install and uninstall Themis JNI library:
themis_jni_{install,uninstall}
The library is installed to
$(jnidir)
which is set to$(libdir)
by default, but can be overriden. This is because Java is not required to look into standard system directories for JNI libraries and may have a different opinion about that.Add a separate package called
libthemis-jni
with Themis JNI library used by JavaThemis wrapper. It depends on Themis Core library against which it is linked. Since we maintain backwards compatibility it should be possible to upgrade Themis Core independently and we allow later versions to satisfy the dependency.Debian and CentOS systems have different opinions about location of JNI libraries. Use
jnidir
to adjust for that.Java installations are not required to look into system library directories. While normally OpenJDK and Oracle JDK installations do look into some directory in the /usr hierarchy, none of the systems that we support looks into
/usr/local/lib
where we install by default when compiling from source.This is particularly important for macOS where Homebrew cannot (realistically) install into any of the standard directories.
Checklist
Change is covered by automated tests(CircleCI does not test DEB/RPM, we’ll check with internal build system)
Benchmark results are attached(not applicable)Example projects and code samples are updated(no API changes)