Situation
My project uses CMake and compiles without problems on Ubuntu 16.04.
When starting the compiled application I get the message cannot open shared object file.
All the shared object libs are available in the same non-standard folder (and I need them there).
- For some reason some can be found, but others cannot.
What I need
- The reason why some shared objects can be found and others cannot be found. The project is pretty big with many CMake files. I tried to find the differences between the libs that can be loaded and the ones that can't, but without success. Any help that point me to the right place is welcome.
- A solution within CMake to make it find all the shared objects.
ldd
The ldd output shows me that most shared objects can be found. Here are some examples:
libboost_filesystem.so.1.55.0 => /path/to/libs/boost/lib/libboost_filesystem.so.1.55.0 (0x00007f2ed1fa0000)
libboost_filesystem.so.1.55.0 => /path/to/libs/boost/lib/libboost_filesystem.so.1.55.0 (0x00007f96af1f5000)
libboost_program_options.so.1.55.0 => /path/to/libs/boost/lib/libboost_program_options.so.1.55.0 (0x00007f96aef85000)
libboost_system.so.1.55.0 => /path/to/libs/boost/lib/libboost_system.so.1.55.0 (0x00007f96aed80000)
For some reason a few others cannot be found. For example:
libboost_iostreams.so.1.55.0 => not found
libboost_chrono.so.1.55.0 => not found
There are other non-boost libs that showing the same behavior, but for simplicity I am just showing the boost examples.
Workarounds already tried
Below are the workarounds that already work successfully. But I am really interested in the two points in the What I need section.
- Copying to standard folders like /usr/lib and running ldconfig
- Adding the path to LD_LIBRARY_PATH
tldr; Check that the imported library is imported as SHARED or UNKNOWN and not STATIC, and has an IMPORTED_SONAME property.
You should check how the library is being imported that you're linking.
I've analyzed a few of the config mode exported targets for static and dynamic libraries, and they are a little different in the properties they set for the target.
For example for zlib, here's the version for static libraries:
However, for dynamic libraries it's:
In a find_package module mode script, you might think you're importing a static library, when in fact the found library is a .so, so it may use the incorrect target properties. In config mode this is not likely because it's much more explicit when defining the target. Though, module mode (cmake/findXXX.cmake), you're often defining these properties as a result of
FIND_PACKAGE_HANDLE_STANDARD_ARGS
_LIBRARIES variable, and it's hard to tell what you're going to get. You can use libFoo.a in the search to be more explicit or playing with CMAKE_FIND_LIBRARY_SUFFIXES.