![写时复制不是基于缺页实现的吗?](https://linux22.com/image/144005/%E5%86%99%E6%97%B6%E5%A4%8D%E5%88%B6%E4%B8%8D%E6%98%AF%E5%9F%BA%E4%BA%8E%E7%BC%BA%E9%A1%B5%E5%AE%9E%E7%8E%B0%E7%9A%84%E5%90%97%EF%BC%9F.png)
操作系统概念说
fork()
我们可以使用一种称为写时复制的技术,该技术的工作原理是允许父进程和子进程最初共享相同的页面。 ...当确定将使用写时复制来复制页面时,重要的是要注意分配空闲页面的位置。许多操作系统为此类请求提供了一个空闲页面池。当进程的堆栈或堆必须扩展或者需要管理写入时复制页面时,通常会分配这些空闲页面。操作系统通常使用一种称为按需填零的技术来分配这些页面。按需填零页面在分配之前已被清零,从而擦除了以前的内容。
写时复制不是基于缺页实现的吗? (我觉得不是)
写时复制和页面错误是否共享同一个空闲页面池?如果没有,为什么? (我觉得不是)
是malloc()
基于缺页错误实现的吗? (我想是的,但不确定为什么它与写时复制共享相同的空闲页面池,如果该池未被页面错误使用)
谢谢。
答案1
(因为这被标记为操作系统,我是在这个背景下回答的。这些都不是 Linux 独有的。)
写时复制不是基于缺页实现的吗?
它基于页面错误。 “复制”页面被标记为只读。当进程尝试写入它们时,CPU 会出现故障,内核会在重新开始写入之前复制该页面。
写时复制和页面错误是否共享同一个空闲页面池?如果没有,为什么?
是的,他们确实这么做了。
是
malloc()
基于缺页错误实现的吗?
malloc()
本身不操作地址空间或分配的页面;它完全由 C 库处理。用于向堆分配内存的函数是brk()
,是的,它依赖于页面错误:分配的页面被标记为不存在。这依赖于相应页表条目中的“存在”位,内核和 MMU 使用该位来跟踪该页面在内存中是否可访问。对不存在页面的任何访问都会导致错误,内核会分配页面并重新启动错误指令。
答案2
Copy on Write
是基于(Memory Management Unit)implicit interrupt
生成来实现的。MMU
页面错误的示例原因如下。
Apage fault
也是由 产生的隐式中断MMU
,但两者不同。页面错误的一些原因如下。
无效内存访问:page fault
当内存中不存在用户进程所需的页面时,就会发生A。Page fault
如果进程想要访问未分配给它的虚拟地址(通常称为segmentation fault
),则可能会发生这种情况。或者,如果页面被换出,也可能会发生这种情况。
写入时复制:a 的一个原因page fault
是Copy On write
.在 fork() 系统调用期间,操作系统为子进程和父进程分配相同的内存,并将内存标记为只读。这节省了巨大的复制损失。假设孩子exec
在之后调用了 a fork
。如果未采用写入时复制,则整个复制页将在 期间被刷新exec
。当父级或子级尝试在该页面上写入时,会产生页面错误。然后操作系统分配一个新页面并删除只读限制。
按需复制:a 的另一个原因page fault
是copy on demand
.当用户进程在其虚拟地址范围内请求新页面时,操作系统可能会分配虚拟地址,而不分配与其相对应的物理地址。当进程尝试访问该页面时,它会生成页面错误。然后操作系统分配与虚拟页相对应的物理页。
所以,页面错误可能不需要分配新页面(在它是由错误生成的情况下)。但是,如果页面错误需要新页面,则该页面来自同一页面池,其中页面在写入时复制到服务器。
malloc
实施与 无关copy on write
。
笔记操作系统可以在没有Copy on Write
和 的情况下工作Copy on Demand
。虽然效果不会很好。但是page fault
操作系统需要支持“分页”的机制