【问题标题】:Linking and Loading of static library静态库的链接和加载
【发布时间】:2020-08-06 21:58:35
【问题描述】:

我的问题是链接器的工作原理。

  • 我正在将一个可执行文件与多个第三方静态库链接。在这些静态库中,只有少数几个被可执行文件使用。在上述情况下,链接器是否只链接到其函数在可执行文件中被引用的库?
  • 如果一个静态库有多个目标文件并且只有一个被可执行文件使用,它是否只链接到那个目标文件?还是它指向整个静态库的链接,但只加载使用的目标文件?

【问题讨论】:

标签: c++ linker loader


【解决方案1】:

对于您的第一个问题,如果没有使用给定库中的符号,则通常不会将其包含在最终产品中。 关于目标文件,链接器可能甚至不会包含完整的目标文件,而只会包含实际引用的符号,尽管您的链接器可能具有更改此行为并导致包含整个库的标志。

【讨论】:

  • 感谢 Coronel 和 Paul 的见解。
【解决方案2】:

...链接器的工作原理。

a) ... 链接器是否仅链接到其函数被引用的库 在可执行文件中?

b) ...静态库有多个目标文件,只有一个被可执行文件使用,它是否只链接到那个目标文件?

这取决于...在 Linux 上,有两种库...“.so”和 .a(存档)。

示例:

 /usr/lib/x86_64-linux-gnu/libgmpxx.a
 /usr/lib/x86_64-linux-gnu/libgmpxx.so

如果您在构建命令的链接部分指定 .a,则只会链接您的应用引用的包含的目标文件(而不是整个库)。这个可执行文件是“独立的”,每个运行的副本都有它自己使用的任何功能的副本。

如果您在构建命令的链接部分指定 .so,并且您的应用程序是第一个使用特定“.so”库的应用程序,我相信您的应用程序将在启动期间短暂暂停,而整个“.so”库已加载。

如果您在构建命令的链接部分指定 .so,并且您的应用不是第一个使用此特定 .so 的应用,那么加载器将向您的应用添加一个映射到已加载的- '.so' 在系统内存中。 (更快的连接)

Executable 使用.so 依赖于系统将.so 库加载到内存中,并将库映射到应用程序内存中并完成应用程序到所需功能的链接。

我相信您的“静态库”对应于“.a”(存档)库的使用。

a) 是 - 当没有更多未解析的引用(对象或函数)时,链接器(有时是链接加载器)“完成”。

b) 是的 - 见 a)

【讨论】:

  • 共享对象 (.so) 可以节省大量内存(与 (.a) 档案相比)。当同时运行大量(相关)应用程序时,每个使用 .a 的应用程序都有一个常用函数的副本。当使用 .so 运行大量(相关)应用时,任何特定(可重入)功能都只有 1 个副本,无论有多少应用使用它。
猜你喜欢
  • 2014-05-31
  • 1970-01-01
  • 1970-01-01
  • 2010-09-15
  • 1970-01-01
  • 1970-01-01
  • 2021-09-19
  • 2014-09-02
  • 1970-01-01
相关资源
最近更新 更多