手机版网站开发html5,苏州建站模板厂家,百度怎么做网站广告,海港开发区人才网目录
一、相关问题
1. 什么是虚拟内存#xff1f;为什么需要虚拟内存#xff1f;
#xff08;1#xff09;内存扩展
#xff08;2#xff09;内存隔离
#xff08;3#xff09;物理内存管理
#xff08;4#xff09;页面交换
#xff08;5#xff09;内存映…目录
一、相关问题
1. 什么是虚拟内存为什么需要虚拟内存
1内存扩展
2内存隔离
3物理内存管理
4页面交换
5内存映射文件
2. 局部性原理
1时间局部性
2空间局部性
3. 什么是内存分段和分页作用是什么
1内存分段
2内存简单分页
3多级页表
那么 为什么不分级的 页表就 做不到这样 节约内存 呢
4段页式内存管理
5分页分段的作用
① 逻辑隔离
② 内存保护
③ 虚拟内存
④ 内存共享
⑤ 内存管理
6分段与分页的区别
① 分段
② 分页Paging
7分段与分页优缺点
4. 解释一下内存页面置换算法
补充快表
1最佳页面置换算法
2先进先出置换算法
3最近最久未使用的置换算法
4时钟页面置换算法 一、相关问题
1. 什么是虚拟内存为什么需要虚拟内存 虚拟内存 在 每一个 进程 创建加载的 过程中会 分配一个 连续 虚拟地址空间它 不是 真实 存在的而是 通过映射 与 实际地址空间 对应这样 就可以 使 每个进程 看起来 都有 自己独立的 连续地址空间并 允许 程序访问 比物理内存 RAM 更大的 地址空间每个程序 都可以 认为它 拥有 足够的 内存来 运行。 需要 虚拟内存的 原因
1内存扩展 虚拟内存 使得 每个程序 都可以 使用 比实际可用 内存 更多的 内存从而 允许运行 更大的程序 或 处理更多的 数据。
2内存隔离 虚拟内存还 提供了 进程之间的 内存隔离。每个进程 都有自己的 虚拟地址 空间因此 一个进程 无法 直接访问 另一个 进程的 内存。
3物理内存管理 虚拟内存 允许 操作系统 动态地 将数据 和 程序的部分 加载到 物理内存中以 满足当前 正在运行的 进程的 需求。当 物理内存不足时操作系统 可以将 不常用的 数据或程序 暂时移到 硬盘上从而 释放内存以便 其他进程 使用。
4页面交换 当 物理内存 不足时操作系统 可以 将一部分 数据从 物理内存 写入到 硬盘的 虚拟内存中这个过程被称为 页面交换。当需要时数据 可以 再次 从虚拟内存中 加载到 物理内存 中。这样 可以保证 系统可以 继续运行尽管 物理内存 有限。
5内存映射文件 虚拟内存 还可以 用于 将文件映射到 内存中这使得 文件的 读取和写入 可以 像访问 内存一样 高效。
2. 局部性原理 在一段时间内程序倾向于 多次访问 相同的 数据 或 接近的 数据而不是 随机地 访问 内存中的 各个位置。局部性原理 通常分为 两种类型时间局部性 和 空间局部性。
1时间局部性 如果 一个数据 被访问那么在 不久的 将来它 很可能会 再次 被访问。这意味着 程序 在短时间内倾向于 反复使用 相同的 数据项。 例如在 循环中 反复访问 数组的 元素。通过 利用 时间局部性程序可以 将频繁 使用的 数据存 储在 缓存中从而 减少访问 主内存的 次数提高程序的 执行速度。 2空间局部性 如果一个 数据被 访问那么 它附近的 数据也 很可能会 被访问这意味着 程序在 访问一个 数据时通常会 在接近 该数据的 附近访问 其他数据。 例如遍历数组时往往会 访问 相邻的 元素。 文件系统在 磁盘上 存储数据时通常会 将相关的 数据块 放在相邻的 磁盘扇区上以便在 访问一个数据块 时能够 快速地 访问相邻的 数据块。 3. 什么是内存分段和分页作用是什么 1内存分段 内存分段是 将一个 程序的 内存空间 分为不同的 逻辑段 segments每个 段 代表程序的 一个功能模块 或 数据类型如 代码段、数据段、堆栈段 等。每个段 都有其 自己的大小 和 权限。 分段机制下的 虚拟地址 由两部分组成段选择因子 和 段内偏移量二维结构。 段选择子就 保存在 段寄存器 里面。段选择子 里面 最重要的是 段号用作 段表的 索引。段表 里面保存的是 这个段的 基地址、段的界限 和 特权等级 等。虚拟地址 中的 段内偏移量 应该 位于 0 和 段界限 之间如果 段内 偏移量是 合法的就将 段基地址 加上 段内偏移量 得到 物理内存地址。 知道了 虚拟地址 是 通过 段表 与 物理地址 进行 映射的分段机制 会把 程序的 虚拟地址分成 4 个段每个段 在段表中 有一个项在 这一项 找到 段的 基地址再加上 偏移量于是就能 找到 物理内存 中的 地址如下图 如果要 访问 段 3 中 偏移量 500 的虚拟地址我们 可以 计算出 物理地址为段 3 基地址 7000偏移量 500 7500。 2内存简单分页 分段的好处 就是能 产生 连续的 内存空间但是会 出现「外部内存碎片 和 内存交换的空间 太大」的问题。要 解决 这些问题那么就要 想出 能少出现一些 内存碎片 的办法。另外当 需要 进行内存交换的 时候让 需要 交换写入 或者 从磁盘装载的 数据 更少一点这样就 可以 解决问题了。这个办法也就是 内存分页Paging。 分页是 把 整个 虚拟和物理 内存空间 切成一段段 固定尺寸的 大小。这样 一个 连续并且 尺寸固定的 内存空间我们叫 页Page。在 Linux 下每一页的大小为 4KB。虚拟地址与物理地址 之间通过 页表 来映射如下图 页表 是 存储在 内存里的内存管理单元MMU就做 将 虚拟内存地址 转换成 物理地址 的工作。而当 进程访问 的 虚拟地址 在 页表 中查不到时系统会 产生一个 缺页异常进入系统内核空间 分配 物理内存、更新 进程 页表最后再 返回 用户空间恢复进程的 运行。 内存分页 由于 内存空间 都是 预先划分 好的也就 不会像 内存分段 一样在 段与段 之间 会产生间隙 非常小的 内存这正是 分段 会产生 外部内存碎片 的原因。 采用了 分页页与页 之间 是紧密排列的所以不会有外部碎片。但是因为 内存分页机制 分配内存的 最小单位是 一页即使 程序 不足 一页大小我们 最少 只能 分配一个页所以 页内 会出现 内存浪费所以 针对 内存分页 机制 会有 内部内存碎片 的现象。 如果 内存空间 不够操作系统 会把 其他 正在运行的 进程 中的「最近 没被使用」的内存 页面 给释放掉也就是 暂时 写在 硬盘上称为 换出Swap Out。一旦 需要的 时候再 加载进来称为 换入Swap In。所以一次性 写入磁盘 的 也只有 少数的 一个页 或者 几个页不会 花太多时间内存交换的效率就 相对比较高。 更进一步地分页的方式 使得 我们 在加载程序的 时候不再需要 一次性 都把 程序 加载到 物理内存中。我们 完全可以 在进行虚拟内存 和 物理内存的 页之间的 映射之后并不 真的 把页 加载到 物理内存 里而是 只有在 程序运行中需要 用到对应 虚拟内存页 里面的 指令 和 数据时再加载到 物理内存 里面去。 在 分页 机制下虚拟地址 分为 两部分页号和页内偏移。页号 作为 页表的索引页表 包含 物理页每页 所在物理内存的 基地址这个 基地址 与 页内偏移的 组合 就形成了 物理内存地址见下图。 总的来说对于一个内存地址转换其实 就是三个步骤 把 虚拟内存地址切分成 页号和偏移量根据 页号从 页表 里面查询 对应的 物理页号直接拿 物理页号加上 前面的 偏移量就得到了 物理 内存地址。 下面 举个例子单个进程虚拟内存中的 页 通过 页表 映射 为了 物理内存中的 页如下图 缺陷 有空间上的缺陷。因为操作系统是可以同时运行非常多的进程的这就意味着页表会非常的庞大。 在 32 位 的环境下虚拟地址空间 共有 4GB假设一个页的大小是 4KB2^12那么就需要大约 100万2^20个页每个「页表项」需要 4 个字节大小来 存储那么整个 4GB 空间的 映射 就 需要有 4MB 的 内存来 存储页表。 每个进程 都是有 自己的 虚拟 地址空间的也就说 都有自己的 页表。那么100 个 进程的话就需要 400MB 的 内存来 存储页表这是 非常大的 内存了更别说 64 位 的环境了。 3多级页表 要解决 上面的 问题就 需要 采用一种 叫作 多级页表Multi-Level Page Table的解决方案。上述 对于 单页表 的实现方式在 32 位 和 页大小 4KB 的环境下一个进程的 页表 需要 装下 100 多万个「页表项」每个 页表项 占用 4 字节 大小相当于 每个 页表 需占用 4MB 大小的空间。 我们把 这个 100 多万个「页表项」的 单级页表 再分页将 页表一级页表分为 1024 个页表二级页表每个表二级页表中包含 1024 个「页表项」形成 二级分页。如下图所示 每个进程 都有 4GB 的 虚拟地址空间而 显然 对于 大多数 程序 来说其 使用到的 空间 远未 达到 4GB因此 会 存在 部分 对应的 页表项 都是空的根本 没有分配对于 已分配的 页表项如果 存在 最近一定时间 未访问的 页表在 物理内存 紧张的 情况下操作系统会 将页面 换出到 硬盘也就是说 不会占用 物理内存。 如果 使用了 二级分页一级页表 就可以 覆盖 整个 4GB 虚拟 地址空间但如果 某个 一级页表的页表项 没有被 用到也就 不需要 创建这个 页表项 对应的 二级页表 了即 可以在 需要时 才创建 二级页表。 做个简单的计算假设 只有 20% 的 一级页表项 被用到了那么 页表 占用的 内存空间 就只有 4KB一级页表20%*4MB二级页表 0.804MB这对比 单级页表 的 4MB 是一个 巨大的节约。 那么 为什么不分级的 页表就 做不到这样 节约内存 呢 从 页表的性质 来看保存在 内存中的 页表 承担的 职责是 将 虚拟地址 翻译成 物理地址。假如 虚拟地址 在 页表中 找不到 对应的 页表项计算机系统 就不能 工作了。所以 页表一定 要 覆盖全部 虚拟地址空间不分级的页表 就 需要有 100 多万个 页表项 来映射而 二级分页 则 只需要 1024 个 页表项此时 一级页表 覆盖到了 全部 虚拟地址空间二级页表在 需要时 创建。 我们把 二级分页 再推广到 多级页表就会 发现 页表 占用的 内存空间 更少了这一切都要 归功于 对 局部性原理的 充分应用。 对于 64 位 的系统两级分页肯定不够了就变成了四级目录分别是 全局页目录项 PGDPage Global Directory上层页目录项 PUDPage Upper Directory中间页目录项 PMDPage Middle Directory页表项 PTEPage Table Entry 4段页式内存管理 内存分段 和 内存分页 并不是 对立的它们是 可以 组合起来 在同一个 系统中 使用的组合起来后通常称为 段页式 内存管理。 段页式内存管理 实现的 方式
先 将程序 划分为 多个 有逻辑意义的 段也就是 前面提到的 分段机制接着 再把 每个段 划分为 多个页也就是 对分段 划分出来的 连续空间再划分 固定大小的 页 这样地址结构 就由 段号、段内页号 和 页内位移 三部分 组成。 用于 段页式 地址变换 的数据结构是 每一个程序 一张段表每个段 又建立 一张页表段表中的地址 是页表的 起始地址而 页表中的 地址则为 某页的 物理页号如图所示 段页式 地址变换 中要得到 物理地址 须经过 三次内存访问
第一次 访问段表得到 页表起始地址第二次 访问页表得到 物理页号第三次 将物理页号 与 页内位移 组合得到 物理地址。 可用 软、硬件 相结合的方法 实现 段页式 地址变换这样虽然 增加了 硬件成本 和 系统开销但提高了 内存的 利用率。 5分页分段的作用
① 逻辑隔离 内存 分段和分页 都实现了 程序的 逻辑隔离使不同的 功能模块 或 数据类型 能够被 单独管理和保护提高了 程序的 可靠性和安全性。
② 内存保护 通过 将不同的 段或页面 设置为 只读、可读写、不可执行等 权限操作系统可以 确保 程序 不会越界访问 或 修改 其他段的 内容从而 提高了 系统的 稳定性。
③ 虚拟内存 分段和分页 都 有助于 实现 虚拟内存 的概念允许 应用程序 认为它们 在使用的是 一个 比实际物理内存 更大的 内存空间。
④ 内存共享 通过 分页操作系统 可以实现 内存页面的 共享从而 节省 内存空间多个进程 可以 共享 相同的代码 或 数据页面。
⑤ 内存管理 分页 更加灵活允许 操作系统 将 不同进程的 页面 分散 存放在 物理内存 中从而 提高 内存利用率。分段 则 更适用于 管理不同的 逻辑模块。
6分段与分页的区别
① 分段
基本单位地址空间 被划分为 不同的 逻辑段每个段 具有 独立的含义如 代码段、数据段等。段的长度每个段的 长度可以 动态变化不同段 的长度 可以不同。内部碎片由于 每个段的 长度 可以 动态变化可能会 导致 内部碎片即 段内部的 未使用空间。外部碎片可能会 导致 外部碎片即 段之间的 未使用空间。逻辑地址逻辑地址 由 两部分组成一个是 段号另一个是 段内偏移。
② 分页Paging
基本单位地址空间 被划分为 固定大小的 页面物理内存 也被 划分为 相同大小的 页面框。页面的长度页面的长度 是固定的由 操作系统 定义。内部碎片由于 页面长度 固定可能会 导致 内部碎片即 页面内部的 未使用空间。外部碎片由于 页面长度 固定不同 页面 之间的 未使用 空间 无法利用可能 导致 外部碎片。逻辑地址逻辑地址 由 两部分组成一个是 页号另一个是 页内偏移。 综述 分页 对用户 不可见分段 对用户 可见。分页的 地址空间是 一维的分段的 地址空间是 二维的。分页单级页表、分段 访问一个 逻辑地址都 需要 两次访存分段存储 中可以 引入 快表机制。分段 更容易 实现 信息的 共享和保护纯代码 或 可重入代码 可以共享。 7分段与分页优缺点 分页管理内存 空间利用率高不会 产生 外部碎片只会有 少量的 页内碎片。但是 不方便 按照 逻辑模块 实现信息的 共享和保护。 分段管理很方便 按照 逻辑模块 实现 信息的 共享和保护。但是如果 段长 过大为其 分配 很大的 连续空间会 很不方便段式管理会 产生 外部碎片。 补充 分页管理将内存划分为固定大小的页这些页并不直接反映程序的逻辑结构。因此很难根据程序的逻辑模块来划分页也很难直接通过页来实现信息的共享和保护。 分段管理将程序的地址空间划分为若干段如代码段、数据段、堆栈段等。这些段与程序的功能模块紧密相关反映了程序的逻辑结构。由于段是按照程序的功能模块划分的因此很容易确定哪些段需要共享哪些段需要保护。 4. 解释一下内存页面置换算法 先说一下 缺页异常缺页中断。 当 CPU 访问的 页面 不在 物理内存 时便会 产生一个 缺页中断请求 操作系统 将所 缺页 调入到 物理内存。那它 与一般 中断的 主要区别 在于
缺页中断 在指令执行「期间」产生 和 处理 中断信号而 一般中断在 一条指令 执行「完成」后 检查和处理 中断信号。缺页中断 返回到 该指令的 开始 重新执行「该指令」而 一般 中断 返回 回到 该指令的「下一个指令」执行。 缺页中断的处理流程如下图 在 CPU 里访问 一条 Load M 指令然后 CPU 会去找 M 所对应的 页表项。如果 该页表项 的状态位是「有效的」那 CPU 就可以 直接去 访问 物理内存 了如果 状态位 是「无效的」则 CPU 则会 发送缺页 中断请求。操作系统 收到了 缺页中断则会 执行 缺页中断 处理函数先会 查找 该页面在 磁盘中的 页面的位置。找到 磁盘中 对应的 页面后需要把 该页面 换入到 物理内存 中但是在 换入前需要在 物理内存中 找空闲页如果 找到 空闲页就把 页面 换入到 物理内存 中。页面 从 磁盘 换入到 物理内存 完成后则把 页表项中的 状态位 修改为「有效的」。最后CPU 重新执行 导致 缺页异常 的指令。 第 4 步 如果 找不到空闲页的话就说明 此时 内存 已满了这时候就需要「页面置换算法」选择一个 物理页如果 该物理页有 被 修改过脏页则 把它 换出到 磁盘然后 把该 被置换 出去的 页表项的 状态 改成「无效的」最后 把 正在访问的 页面 装入到 这个物理页 中。页表项通常有如下图的字段 状态位用于 表示 该页 是否 有效也就是说 是否 在物理内存中供 程序访问时 参考。访问字段用于 记录该页 在一段时间 被访问的 次数供 页面置换算法 选择出 页面时 参考。修改位表示 该页在 调入内存后 是否有被 修改过由于 内存中的 每一页 都在 磁盘上 保留 一份副本因此如果 没有修改在 置换该页时 就不需要 将该页 写回到 磁盘上以 减少 系统的 开销如果 已经 被修改则将 该页 重写到 磁盘上以 保证磁盘中 所保留的 始终是 最新的副本。硬盘地址用于 指出 该页在 硬盘上的 地址通常是 物理块号供 调入 该页时 使用。 所以页面置换算法的 功能是当 出现 缺页异常需 调入 新页面 而内存 已满时选择 被置换的 物理页面也就是说 选择一个 物理页面 换出到 磁盘然后把 需要访问 的页面 换入到 物理页。 补充快表 快表是 一种 特殊的 高速缓冲存储器Cache内容是 页表 中的 一部分 或 全部内容。在操作系统中 引入 快表是 为了 加快 地址映射速度。在 虚拟页式 存储管理 中设置了 快表作为 当前 进程页表的 Cache。通常快表处于 MIMU 中。 按照 逻辑地址 中的 页号 查快表。若该页 已存在 快表 中则由 快表中 记录的 映射信息 和 页内偏移量 形成 物理地址。若该页 不在快表中则 再查 主存页表与 页表中 记录的 映射信息 和 页内偏移量 形成物理地址同时 将该 页表项 登记到 快表中。当 快表 填满后又要 登记 新页时则需要 按照一定 替换策略 淘汰一个 旧的 登记项。 1最佳页面置换算法 最佳页面置换算法 基本思路是置换在「未来」最长时间 不访问的 页面。所以该算法 实现 需要 计算 内存中 每个 逻辑页面的「下一次」访问时间然后比较选择 未来 最长时间 不访问的 页面。 举个例子假设 一开始 有 3 个 空闲的 物理页然后 有请求的 页面序列那 它的 置换过程 如下图 在 这个 请求的 页面序列 中缺页 共 发生了 7 次空闲页 换入 3 次最优页面置换 4 次页面置换 共发生了 4 次。这很理想但是 实际系统中 无法实现因为 程序 访问页面 时是 动态的我们是 无法 预知 每个 页面在「下一次」访问前的 等待时间。 所以最佳页面置换算法 作用是 为了衡量 你的算法的 效率你的 算法 效率 越接近 该算法的 效率那么 说明你的 算法是 高效的。 2先进先出置换算法 无法 预知页面在 下一次访问 前 所需的 等待时间那可以 选择在 内存驻留 时间 很长的页面 进行中 置换这个就是「先进先出置换」算法的 思想。 以前面的 请求的 页面序列作为例子假设使用先进先出置换算法则过程如下图 在这个 请求的 页面序列中缺页共发生了 10 次页面置换 共发生了 7 次跟 最佳页面 置换算法 比较起来性能 明显差了 很多。
3最近最久未使用的置换算法 最近最久未使用LRU的置换算法的 基本思路 是发生缺页时选择 最长时间 没有 被 访问的页面 进行置换也就是说该算法 假设 已经 很久 没有 使用的 页面 很有可能 在未来 较长的 一段时间内 仍然不会 被使用。 这种算法 近似 最优置换算法最优置换算法是 通过「未来」的 使用情况 来 推测 要淘汰的 页面而 LRU 则是 通过「历史」的 使用情况 来推测 要淘汰的 页面。 以前面的 请求的 页面序列作为例子假设 使用 最近最久未使用的 置换算法则过程如下图 在这个 请求的 页面序列 中缺页 共 发生了 9 次页面置换 共 发生了 6 次跟 先进先出 置换算法比较 起来性能 提高了一些。虽然 LRU 在理论上是 可以实现的但 代价很高。 为了 完全 实现 LRU需要 在内存中 维护一个 所有 页面的 链表最近 最多使用 的 页面在 表头最近最少 使用的 页面在 表尾。困难的是在 每次访问 内存时 都 必须要 更新「整个链表」。在 链表中 找到一个 页面删除它然后把 它移动到 表头是 一个 非常 费时的 操作。所以LRU 虽然看上去 不错但是 由于开销 比较大实际 应用中 比较少 使用。 4时钟页面置换算法 那 有没有一种 即能 优化置换的 次数也能 方便实现的 算法呢 时钟页面置换算法 就可以 两者兼得它跟 LRU 近似又是对 FIFO 的 一种改进。 该算法的 思路是把 所有的 页面都 保存在 一个类似 钟面的「环形链表」中一个 表针 指向 最老的 页面。当 发生缺页 中断时算法 首先 检查 表针 指向的页 面
如果 它的 访问位 是 0表示该页面最久未被访问可以选择进行置换然后 淘汰 该页面并 把新的 页面 插入 这个位置然后 把表针 前移 一个位置。如果 访问位 是 1表示该页面最近被访问过它仍然处于活跃状态然后 清除 访问位并把 表针 前移一个 位置重复 这个 过程 直到 找到了 一个访问位 为 0 的 页面 为止。 时钟页面置换算法的 工作流程图如下