动态链接-Linux与。视窗

Ben*_*y K 10 c c++ linux windows shared-libraries

在Windows下,当我在MSVC的DLL项目中编译C / C ++代码时,我得到2个文件:

  1. MyDll.dll
  2. MyDll.lib

据我了解,MyDll.lib其中包含某种指示符表,用于指示dll中的函数位置。使用此dll时(例如在exe文件中),MyDll.lib在链接期间会嵌入到exe文件中,因此在运行时它“知道”函数的位置MyDll.dll并可以使用它们。

但是,如果我在Linux下编译相同的代码,我只会得到一个MySo.so不带 文件的文件MySo.a(相当于libLinux中的文件),那么MySo.so如果在链接过程中未嵌入任何内容,Linux下的可执行文件如何知道函数的位置?

rus*_*tyx 6

MSVC 链接器可以将对象文件 (.obj) 和对象库 (.lib) 链接在一起以生成 .EXE 或 .DLL。

为了与 DLL 链接,MSVC 中的过程是使用所谓的导入库 (.LIB),它充当 C 函数名称和 DLL 导出表之间的粘合剂(在 DLL 中,函数可以按名称或通过-后者通常用于无证的API)。

但是,在大多数情况下,DLL 导出表包含所有函数名称,因此导入库 (.LIB) 包含大量冗余信息(“导入函数 ABC -> 导出函数 ABC ”等)。
甚至可以从现有的 .DLL生成.LIB。

其他平台上的链接器没有这个“特性”,可以直接与动态库链接。


JL2*_*210 2

在 Linux 上,链接器(不是动态链接器)搜索链接时指定的共享库,并在可执行文件内创建对它们的引用。当动态链接器加载这些可执行文件时,它将它们所需的共享库加载到内存中并解析符号,从而允许运行二进制文件。

MySo.a如果创建的话,实际上会包含直接链接到二进制文件的符号,而不是 Windows 上使用的“符号查找表”。

rustyx 的回答比我更彻底地解释了 Windows 上的过程;我已经很久没有使用Windows了。