题
我想要 dlopen() 特定目录中的每个共享库。为了做到这一点,
检索 linux 库搜索路径的最简洁方法是什么。或者是否有更快的方法来查找该路径中的特定目录?
posix 会更好。
解决方案
POSIX 不支持查找共享库搜索路径上的目录的机制(它不强制要求 LD_LIBRARY_PATH
, ,例如),因此任何解决方案本质上都是特定于平台的。
Linux 存在一些问题,因为要使用的值可能基于以下内容: /etc/ld.so.conf
以及任何运行时值 LD_LIBRARY_PATH
环境变量;其他系统也存在类似的问题。默认位置也因系统而异 - 其中 /lib
和 /usr/lib
对于 32 位 Linux 机器来说很常见,但是 /lib64
和 /usr/lib64
至少在某些 64 位机器上使用。但是,其他平台使用 64 位软件的其他位置。例如,Solaris 使用 /lib/sparcv9
和 /usr/lib/sparcv9
, ,例如(尽管文档提到 /lib/64
和 /usr/lib/64
, ,它们是符号链接 sparcv9
目录)。Solaris也有环境变量 LD_LIBRARY_PATH_64
和 LD_LIBRARY_PATH_32
. 。HP-UX 和 AIX 传统上使用除 LD_LIBRARY_PATH
-- SHLIB_PATH
和 LIBPATH
, IIRC ——虽然我相信 AIX 现在使用 LD_LIBRARY_PATH
也。并且,在 Solaris 上,用于配置共享库的工具是“crle”(配置运行时链接环境)以及类似的 /etc/ld.so.conf
或者是 /var/ld/ld.config
或者 /var/ld/64/ld.config
. 。当然,共享库的扩展也各不相同(.so
, .sl
, .dylib
, .bundle
, , ETC)。
因此,您的解决方案将是特定于平台的。您需要决定默认位置、要读取的环境变量、要读取的配置文件以及相关的文件扩展名。鉴于这些,那么它主要是 SMOP - 简单的编程问题:
- 对于由任何来源命名的每个目录:
- 打开相关子目录(
opendir()
)- 读取每个文件名(
readdir()
) 反过来 - 使用
dlopen()
在相关文件的路径上。 - 进行与您相关的任何分析。
- 使用
dlclose()
- 读取每个文件名(
- 使用
closedir()
- 打开相关子目录(
另请参阅下面评论中的注释...整个主题在不同平台上略有不同。
其他提示
我不知道这是可能做到这一点,是便携式的。由于这个问题是关于Linux,便携性可能不是最重要的。那我就不明白了POSIX约束。你能否澄清?
您可能会不得不要么实现man 8 ld.so
详细的搜索功能,其中包括除了扫描/etc/ld.so.conf中来LD_LIBRARY_PATH
,或者使/lib/ld.so
你想要做什么你和解析输出。对于有未准确-相当的命令行可以是:
export LD_PRELOAD=THISLIBRARYSODOESNOTEXIST
strace -s 4096 /bin/true 2>&1 | sed -n 's/^open("\([^"]*\)\/THISLIBRARYSODOESNOTEXIST".*$/\1\/YOURSUBDIRHERE/gp'
unset LD_PRELOAD
您可以再与POSIX文件罗列调用opendir(3)
和readdir(3)
。