4

This question asks how to install a shared library with cmake which has been imported rather than being built by the current project:

Can I install shared imported library?

To repeat the issue:

add_library(libfoobar SHARED IMPORTED)
# this install command is illegal
install(TARGET libfoobar LIBRARY DESTINATION "${RPMBUILDROOT}${LIBDIR}")

This was raised as a [https://gitlab.kitware.com/cmake/cmake/issues/14311|issue] with cmake that has been closed, effectively with a resolution of will not fix. The grounds are, quite reasonably, that cmake does not know enough about an imported target to reliably install it.

One point the answer to that question misses is that install(TARGET) will automagically create links from libfoo.so to libfoo.so.major and libfoo.so.minor version on GNU/Linux and other unix-like platforms where this is required.

Is there a way to hijack cmake into treating a custom target as if it was built by the project or otherwise persuade it to create those links? Something like:

add_library(libfoobar SHARED IMPORTED)

#? add_custom_target(X libfoobar) 
install(TARGET X LIBRARY DESTINATION "${RPMBUILDROOT}${LIBDIR}")

What is a canonical way to do this?

Bruce Adams
  • 4,953
  • 4
  • 48
  • 111

1 Answers1

-1

When a library is built by CMake, it is CMake who assigns soversion numbers to it (according to project's settings).

When a library isn't built by CMake, CMake doesn't know soversion, so it cannot create symlinks for you.

If you bother about that CMake actually installs symlink instead of file, resolve symlinks before installing, like in that question.


Well, you may ask CMake to guess soversion of the library (e.g. by resolving symlinks and checking their names). But why you ever need symlinks?

The main purpose of soversion symlink is to resolve compatibility issues with the future library's updates. But updates are possible only when the library is installed by the project who creates it.

If your project installs library produced by other project, it is unlikely that you want to support updates for the local library's installation. So there is no needs for you to support soversions.

Tsyvarev
  • 60,011
  • 17
  • 110
  • 153
  • With regards to the first point. cmake **could in principle** obtain the soversion if it wants to just as I can obtain it myself using for example `objdump -x libfoo.so | grep SONAME`. cmake clearly has a place to store that information internally (as you say via the properties) but I don't know of a user accessible (i.e. scriptable) way of setting it. Can you set properties on an imported library? – Bruce Adams Jul 21 '17 at 11:46
  • With regards to the second point a good reason is given in the discussion of https://stackoverflow.com/questions/45237394/is-there-a-way-to-set-the-elf-needed-field-at-link-time Unless you know a better way of setting NEEDED on an ELF binary creating the symbolic links would seem to be the less hacky option. – Bruce Adams Jul 21 '17 at 17:01