dlopen与标准动态链接的用例有哪些?

根据文档, dlopen与dlsym一起使用来加载库,并获得指向符号的指针。

但这已经是动态加载器/链接器的作用了。 而且,这两种方法都基于ld.so.

使用dlopen时似乎有两个不同之处:

  1. 该库可以有条件地加载。
  2. 编译器不知道我们正在使用的符号(类型,原型……),因此不会检查潜在的错误。 顺便说一句,这是实现内省的一种方式。

但是,除了边缘的例子之外,它似乎没有激励使用dlopen不是标准加载:

  1. 在内存占用优化方面,当共享库已经被另一个程序使用时,条件加载并不是很有趣:加载已经使用过的库并不会增加内存占用。
  2. 避免编译器监控是不安全的,也是编写错误的好方法……我们也错过了潜在的编译器优化。

那么,还有其他用途,其中dlopen优先于标准的动态链接/加载吗?

那么,还有其他用途,其中dlopen优先于标准的动态链接/加载吗?

使用dlopen典型用例是

  • 插件
  • 选择当前CPU的最佳实现(英特尔数学库这样做)
  • 选择不同供应商的API实现(GLEW和其他OpenGL包装器这样做)
  • 延迟加载共享库如果不太可能使用(这会加快启动速度,因为库构造函数不会运行+运行时链接器的工作量会稍微减少)

避免编译器监控是不安全的,也是编写错误的好方法……我们也错过了潜在的编译器优化。

这是真的,但通过在延迟加载的共享库周围提供一个小的包装器库,你可以拥有两全其美。 在Windows上,这是通过标准工具(谷歌“DLL导入库”)完成的,在Linux上你可以手动完成或使用Implib.so 。

我在Windows环境中这样做以构建语言切换function。 当我的应用程序启动时,它会检查配置设置应该使用哪个language.dll。 从现在开始,所有文本都从动态加载的库中加载,甚至可以在运行时替换。 我还包括一个格式化序列(第1,第2,第3)的函数,它是特定于语言的。 我的母语语言资源包含在可执行文件中,所以我最终根本没有可用的文本。

关键是可执行文件可以在运行时决定应该加载哪个库。 在我的情况下,它是一个语言切换,或者评论员说像插件的目录扫描。

缺乏对呼叫签名的监控肯定是一个缺点。 如果你真的想做一些邪恶的事情,比如重写原型类型定义,你可以使用标准的C类型转换来做到这一点。