将符号限制为适用于linux可执行文件的本地范围

任何人都可以请build议一些方法,我们可以限制我们的符号出口到全球符号表?

提前致谢


嗨,

感谢回复…

其实我有一个静态链接到第三方库的可执行文件说“ver1.a”,也使用第三方“.so”文件再次链接到相同的库,但不同的版本说“ver2.a”。 问题是执行这两个版本是不同的。 在开始时,加载可执行文件时,来自“ver1.a”的符号将被导出到全局符号表。 现在无论何时“.so”被加载,它将尝试引用ver2.a中的符号,它将最终引用之前加载的“ver1.a”中的符号,从而导致我们的二进制文件崩溃。

我们想到了一个解决scheme,我们不会将可执行文件的符号导出到全局符号表中,因此当“.so”被加载并尝试使用来自ver2.a的符号时,它不会在全局符号表中find它,并且将使用它自己的符号,即来自ver2.a的符号

我无法find任何方式,我可以限制符号导出到全局符号表。 我试着用–version脚本和保留 – 符号文件,但它没有奏效。 对于-fvisibility = hidden选项,它提供了一个错误,“-f选项只能与-shared一起使用”。 所以我想,这也像“ – 版本脚本”只适用于共享库不可执行的二进制文件。

代码在c ++,OS-Linux,gcc版本-3.2。 可能无法重新编译任何第三方库和“.so”。 所以排除了用bsymbolic标志重新编译“so”文件的选项。

任何帮助,将不胜感激。

用dlopen拉入第三方库。

你也许可以通过创建你自己的隐藏所有第三方符号的共享库来避免这种情况,并且只暴露你自己的API,但是如果所有其他的都失败了,dlopen就会给你完全的控制权。

我有,听起来像一个类似的问题/问题: 在C ++插件库与重复符号Segfault

如果你可以重建第三方库,你可以尝试添加链接标志-Bsymbolic (gcc / g ++的标志是-Wl,-Bsymbolic )。 这可能会解决你的问题。 这一切都取决于你的代码和东西的组织,因为有使用它的注意事项:
http://www.technovelty.org/code/c/bsymbolic.html
http://software.intel.com/en-us/articles/performance-tools-for-software-developers-bsymbolic-can-cause-dangerous-side-effects/

如果你不能重建它,根据第一条警告链接:

实际上,构建共享库时,-Bsymbolic标志唯一的作用是在名为DT_SYMBOLIC的二进制文件的动态部分添加一个标志。

所以也许有办法将DT_SYMBOLIC标志添加到动态部分后链接?

最简单的解决方案是重命名可执行文件中的符号(通过更改源代码),以便它们不会与共享库发生冲突。

下一个最简单的事情就是用'objcopy -L problem_symbol'来定位“问题”符号。

最后,如果你不直接链接到第三方库(而是像bmargulies建议的那样直接打开它), 你的其他共享库没有使用定义“问题”符号, 而且你也不用链接到-rdynamic或者它的一个等价物,那么这个符号不应该被导出到可执行文件的动态符号表中,因此你不应该有冲突。

注意: 'nm a.out' 仍然会显示全局定义的符号,但这对于动态链接无关紧要。 你想用'nm -D a.out'来查看a.out动态符号表。