一个应用中

时间:2017-11-10 12:53:15

标签: c++ compilation linker

我有两个相同共享库的版本(几乎相同的API)。我必须在同一个应用中使用它们。我知道如何解决标题中的名称冲突 - 我将像这样导入它们

namespace version1 {
    #include "version1/library.h"
}

namespace version2 {
    #include "version2/library.h"
}

我不知道如何解决链接冲突 - 库是动态链接的。第一个版本在自定义lib文件夹中创建以下结构:

libsomething.so -> libsomething.so.2
libsomething.so.2 -> libsomething.so.0.8.31.1
libsomething.so.0.8.31.1
第二个:

libsomething.so -> libsomething.so.2
libsomething.so.2 -> libsomething.so.0.8.32
libsomething.so.0.8.32

我的目标环境是Linux机器。

上下文:

我有库的源代码,但它们是自动下载和编译的,所以我想避免在这些库的CMakeProject中更改任何内容,但如果其他选项变得复杂,我可以这样做。我更喜欢在编译后对这些库进行更改的解决方案,例如改变soname。但是,如果我必须在应用程序代码中做一些复杂的东西来使用这些库,我更喜欢对这些库项目进行更改并维护它们(因为版本可以改变,但总会有两个 - 一个版本可能永远设置并且从未更新过,所以我更愿意更改此不变版本。)

1 个答案:

答案 0 :(得分:0)

  

我的目标环境是Linux机器。

基于符号链接的两个版本的库似乎都具有相同的SONAME,即libsomething.so.2

这完全排除了将它们链接到相同的可执行文件,并使用Linux的运行时加载程序在运行时加载它们。它没有这种能力。

我看到的唯一选项是您的可执行文件使用dlopen(3)库调用手动加载每个库。之后,您需要使用dlsym(3) or dlsymv3(3)在每个加载的库中查找每个函数的地址,并间接调用它。

请注意dlsym()dlsymv3()采用每个函数名称的错位版本。它会由你决定每个函数的错误名称是什么。

没有人声称这很容易,但是当绝对没有其他选择时,这是可行的。