Java build questions

Hi all - happy to say we are having great success building and using VTK 9 in our upgraded tool. We did have a few questions related to the overall Java build process though.

  • First, when the jnilibs are built, they end up pointing to dylib/.so/.dll files, which in and of itself is fine, but the directory where those live have the main file with content, a symlink to that, and THEN a symlink to the symlink (at least for mac and linux). This seems… wrong? Can anything be done in your scripts to eliminate those unnecessary files? Can the jnilibs replace the other libraries entirely, so there is only one set of files to reference?

  • Second, are there any plans in the future of supporting pre-built versions of VTK? It would be nice to not have to compile it from scratch every release…


@ben.boeckel might have some insight on both points.

Given the number of platforms and compilers supported by VTK, I wouldn’t count on any pre-built binaries in the future. CMake exists to mitigate this.

This is the way shared libraries work on these platforms (well, maybe less on macOS, but it’s a similar thing). You have:

  • This is the file that the linker looks for with -lfoo
  • This is the “soname” file that the runtime loader looks for. Libraries with the same soname should be ABI compatible with each other (using symbol versioning to indicate new APIs). This is rare in practice (effectively only glibc, libstdc++, X11, glib, Qt, and low-level KDE/GNOME libraries ever actually accomplishing this in practice)
  • This is the implementation file that actually contains the code. It claims a soname of the relevant link that comes with it.

We could add a build flag to maybe remove those, but it feels like one of those flags that someone sets out of curiosity then wonders why they have a weird install.

Eh, that means compiling VTK’s C++ code into the jnilibs. That is unlikely to happen for a shared build (but might be possible with a static build?).

To be fair, back in 2005 that was my favorite way to built the Python modules. The use of RTLD_GLOBAL allowed the modules to promiscuously share the C++ symbols, which made shared C++ libraries unnecessary for the Python wrappers. I’m happier with the way things are now, though (clean dependencies, controlled visibility).

OK so followup question to this (and thanks for the explanation). From spot checking a few jnilibs, it looks like they either point (by running otool -l on the jnilib) to other jnilibs OR the 9.0.1 version of another dylib. The 9.0 versions are never referenced. The 9.0.1 versions all seem to just be pointers to the file which is the “Real” file. (This is on a mac btw)

libvtkRenderingContextOpenGL2-9.0.1.dylib -> libvtkRenderingContextOpenGL2-
libvtkRenderingContextOpenGL2-9.0.dylib -> libvtkRenderingContextOpenGL2-9.0.1.dylib

So given this heavy use of soft links/aliasing, would there be an issue if we just renamed the file to 9.0.1, and eliminated the other soft links when we go to distribute our application? They seem unnecessary. I know they are soft links, so they don’t consume a ton of space, but why distribute what we don’t need to, right?

Also: I expected that response about pre-built libraries. Figured I could at least ask :slight_smile:


Symbolic links enable multiple versions of a library to happily coexist on a user’s system. A developer can then link to the currently installed version, a particular major released version or even a specific minor patched version. Why would you want to break that? It is standard practice on Linux systems.

Sorry - should have stated up front that we don’t install VTK into a user’s system, we ship it along with our Java code and refer to the local libraries on launch, meaning the symbolic links don’t do a lot for us.

So you’re building a stand-alone Java app with the VTK shared libraries copied into a custom (sub) folder? In that case you don’t need the symbolic links.

The folder is probably an .app bundle, since that’s a common way to distribute software on macOS. Libraries included within the bundle are generally found via @executable_path (executable to library) and @loader_path (library to library) so, yes, the presence of symlinks is unnecessary and a bit silly.