如何减少动态库加载时间?

How to reduce dynamic library loading times?

我有一个关于减少加载程序所需时间的问题。

我有一个链接到 189 个共享库的二进制文件。我用 perf 分析了二进制文件,GNU 加载器 ld.so 占用了我程序 运行 时间的 40%,大约 90 毫秒。

有什么方法可以优化动态库加载时间,还是我被迫使用静态链接?

我运行这个程序很多次了。

加载时间取决于几个因素:将库从媒体存储传输到内存所需的时间、链接的符号数量...这里有一些建议:

  1. 如果使用dlopen(),可以设置惰性绑定标志(RTLD_LAZY)
  2. 确保 ld.so.cache 是最新的,使用 ldconfig (and update ld.so.conf if necessary) to improve the library search time. Using strace 可能有助于查看查找库文件的尝试次数。还要检查 LD_LIBRARY_PATH 环境变量。
  3. 确保 LD_BIND_NOW 环境变量未设置为使动态链接器 (ld.so) 运行 处于惰性模式
  1. 避免库中的 C++ 构造函数,因为它们会导致 运行 构造函数本身的延迟,用于解析符号和从硬盘驱动器加载代码
  2. 通过使用 -fvisibility=hidden 编译库(并有选择地使用 __attribute__((visibility("default"))) 用于您确实要导出的符号)来最大程度地减少导出符号的数量
  3. 使用--as-needed 最小化库依赖性
  4. 确保启用延迟绑定(即未设置 LD_BIND_NOW 并且库未使用 -Wl,-z,now 编译)
  5. 终于可以使用Prelink工具静态预计算符号偏移

可以通过导出来测量库加载时间LD_DEBUG=statistics