Compiled shared library has dependency on specific libicuuc.so.46 version

2k views Asked by At

I am compiling a shared library using g++ on SUse Linux with cmake that depends on libicuuc.so and friends.

Suse has libicuuc.so, libicuuc.so.46 and libicuuc.so.46.1 in /usr/lib.

Now when I use ldd to list the dependencies of my library it tells me that it depends on libicuuc.so.46.

Since I want to distribute my library in binary form (it takes about 45 minutes to compile on a fast PC) this dependency is a problem. The target PCs have different versions of libicuuc.so.

What can I do so that my library depends on libicuuc.so and not libicuuc.so.46?

I tried to remove the so.46 versions in my /usr/lib folder before compiling but libicuuc.so depends on libicudata.so.46 so I keep that dependency on a 46 version what I try to avoid.

1

There are 1 answers

4
Employed Russian On BEST ANSWER

Read about external library versioning here.

What can I do so that my library depends on libicuuc.so and not libicuuc.so.46?

You can't do anything about that. The libicuuc.so that you have has SONAME set to libicuuc.so.46, and the linker dutifully records that dependency (as it should).

If developers release libicuuc.so.47, they would do so because the new library is not ABI-compatible with the old one (at least that's what they should do if they are not clueless).

If your library loaded libcuuc.so.47 (as you want it to), it would most likely crash due to the ABI incompatibility. Or worse: corrupt your end user's data. So achieving your desired result would get you into worse trouble than what you have now (not running is better than randomly crashing or corrupting data).

Update:

The libicuuc.so documentation explicitly states that "Binary compatibility is for versions that share the same major+minor number."

That means: you can't link a library compiled with version 4.6 (SONAME libicuuc.so.46) and expect it work with version 4.7.

You must either rebuild your library for each version of ICUUC, or distribute matching libicuuc.so.NN with your library (and hope that the user is not already using some other version of libicuuc).

Another possible alternative: statically link libicuuc.a into your library, and hide all of libicuuc.a symbols so they don't conflict with anything else. Note: this has licensing implications.