共享库地址空间

12

在我学习共享库的时候,我读到了一句话:

尽管共享库的代码被多个进程共享,但它的变量并不被共享。使用该库的每个进程都有自己的全局和静态变量的副本,这些变量在库中定义。

我只有几个疑问。

  1. 每个进程的代码部分是否在单独的地址空间中?
  2. 共享库的代码部分是否在某个全局(唯一)地址空间中?

我是一个初学者,请帮助我理解。

谢谢!


这是“process”,而不是“progress”。 - Marcelo Cantos
2
请查看此链接:http://duartes.org/gustavo/blog/post/anatomy-of-a-program-in-memory。它很好地解释了程序在内存中的情况。您可以看到共享库通常被映射到进程的虚拟地址空间中。 - another.anon.coward
1个回答

27

共享库通过将文件映射到进程地址空间的某个部分来加载到进程中。当多个进程加载同一个库时,操作系统只需让它们共享同一块物理内存。

可修改的库部分(例如静态全局变量)通常以写时复制模式加载,因此当尝试进行写操作时,会发生页面错误,内核通过将受影响的页面复制到另一个物理内存页面(仅针对该进程),重新映射到新页面,然后才最终完成写操作。

回答您的具体问题:

  1. 所有进程都有自己的地址空间。进程之间的物理内存共享对每个进程是不可见的(除非它们通过共享内存API故意这样做)。
  2. 所有数据和代码都驻留在物理内存中,这是一种地址空间。但你看到的大多数地址实际上是虚拟内存地址,属于一个进程或另一个进程的地址空间,即使那个“进程”是内核。

那么即使通过库的静态链接生成可执行程序,这也适用吗? - Sandeep
@Sandeep 是和不是。静态库成为可执行文件的一部分,不与其他程序共享。然而,可执行文件本身以与共享库相同的方式加载,并与程序的其他运行实例共享,写入由我描述的方式管理。 - Marcelo Cantos

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接