操作系统笔记-7-虚拟内存

引言

上一篇笔记讲述了内存的地址空间抽象,但是还留下了问题,那就是当软件很大的时候虽然利用Swapping技术可以运行,但是每次交换整个进程的空间开销不容忽视,虽然近年来内存也有增长,但是软件大小增长的速度远大于内存增长的速度。

一个解决方法是Overlays(覆盖),Overlays将程序分割为多个片段,称为覆盖,当程序开始时,覆盖管理器加载覆盖0,执行完成后,通知覆盖管理器加载覆盖1,然后覆盖1会在覆盖0top上(如果有空间),或者直接在覆盖0(如果没空间)。虽然,换入换出覆盖块由操作系统完成,但是需要程序员将程序分块,这是一个复杂的工作,并且非常容易出错。因此这种技术无法普及,因此人们又提出了新的解决方案,这次是完全交给系统完成,那就是今天要学习的一个技术-虚拟内存。

基本概念
原理

每个程序都有自己独立的空间,并且这个空间分了多个固定大小的块,这些块通常叫做,每一个页都有一个连续的地址范围,每一个页都映射一个物理范围叫页框(页框的大小通常和页是一样),程序运行不需要所有的页都在内存中,当程序引用到在物理内存中的地址空间时,由硬件(MMU)完成映射;如果不在内存中,由操作系统载入内存并重新执行失败的指令。

页框

物理内存中对应虚拟内存的页叫页框,大小和虚拟内存页大小一致。(RAM和磁盘交换数据是以页为单位的。有不同页面大小混合使用的)

虚拟地址
  • 虚拟地址是程序在虚拟空间生成的地址,类似于上一篇讲的逻辑地址,它不是真实的物理地址,需要通过一定的转换才能得到物理地址。

  • 简单虚拟地址结构,分为两部分,前n位表示页编号,后m位表示偏移量
    在这里插入图片描述

  • 一个例子:假设一个系统页大小为4Kb,而应用程序需要的空间为64Kb,虚拟页有16个,因此页编号需要4位,而偏移量需要12位,总共16位就可以表示虚拟地址

页表
  • 页表是一个列表项的集合,最简单的虚拟地址分为两部分,前n位表示的页编号便是页表的索引(这里的页表是很简单的页表,后边在讲如何解决大虚拟内存时会讲到多级页表)

  • 页表项示意图
    在这里插入图片描述

    • Present/absent位,表示虚拟页是否在内存中

    • 保护位,简单用一个位0-r/w,1-只读。或者用3个位,分别表示可读、可写和可执行

    • 修改位,当一个页面被写入时该位会自动修改,表示该页是脏的

    • 引用位,当一个页面被访问时,该位会被设置,它的值可以用来帮助OS在缺页时选择被淘汰的页面

    • 禁止缓存位,设置该位代表该位禁止被缓存,用于I/O设备,如果I/O设备有独立的内存空间,该位不需要使用

  • 不同计算机的页表项大小可能不同

内存管理单元(MMU)
  • 作用: 解析虚拟地址映射的物理地址,数学形式: F ( V A ) = P A F(VA) = PA F(VA)=PA

  • MMU工作示意图
    在这里插入图片描述

  • 虚拟内存映射物理内存示意图
    在这里插入图片描述

    上图是程序的虚拟空间64K,内存是32K,页和页框为4K,可以看到0-4095映射到8192-12287

  • MMU映射过程

在这里插入图片描述

  • MMU内部处理流程
    1. 虚拟地址8196取出高4位计算页表索引,0010表示2,因为找到索引为2的页表项
    2. 通过Present/absent位判断虚拟页是否在内存中,此处的值为1,说明在内存中,找到页框号110;否则MMU发现虚拟地址找不到映射的物理地址,使CPU陷入操作系统(缺页中断),OS会选择一个很少使用的页框交换出去,重新执行陷入OS的指令
    3. 将页框号+上偏移量就是物理内存地址,放到bus上
分页问题
加速分页-TLB
  • 分页系统面临的两个问题

    1. 虚拟内存地址映射为物理内存地址必须快
    2. 如果虚拟地址空间很大,那么页表空间也要很大
  • 解决方案-TLB(转换检测缓冲区)

    • 原理:通过观察,大部分的程序多数情况都是反复访问很少的的页,也就是说,只有很少的页被反复访问,大多数页很少访问,TLB硬件一般在MMU里。TLB示意图
      在这里插入图片描述
  • MMU硬件TLB管理

    当TLB失效时,有MMU硬件负责查找并且装载,主要的好处是一个简单的MMU可以节省芯片的很多空间让给缓存和其他可以提升性能的组件,TLB工作原理图
    在这里插入图片描述

  • 软件TLB管理

    当TLB失效时,会生成一个TLB失效并将问题交给OS解决,查找和装载TLB由OS完成

    • 减少TLBmiss:OS会预加载,系统推断接下来需要使用的页
    • 降低TLB miss时的开销
      • 存在问题:如果用软件管理TLB,当TLB实现时,会通过搜索页表索引页,假如此时存放页表的页不在TLB中,就会引起二次TLB失效
      • 解决办法:在内存上固定区域维护一个大(比如4KB)的TLB表项的缓存,该固定区域的页一直在存在TLB中,当TLB实现时,先查找TLB的缓存
    • TLB miss类型
      • soft miss(软失效):TLB未命中,但是页在内存中
      • hard miss(硬失效):TLB未命中,且页不在内存中,开销将非常高
      • minor page fault(次要缺页错误):页不在该进程的页表中,但是在内存中,在其他进程的页表中,这一种只需要在进程的页表中简单的更新映射
      • major page fault(严重缺页错误):页需要从磁盘调入
      • segmentation fault(段错误):程序访问非法地址
大内存页表问题
  • 问题:如果内存非常大,那么页表也很大,比如4G的内存,采用4KB的页大小,那么页表将有100w个页表项,因为页可能分散在内存的各个页框,所以需要维护这个包含100w个页表项的页表,并且有多少个进程就有多少个这种页表,非常浪费空间。

  • 分级页表

    • 原理:采用多级的设置,可以避免始终保持所有的页表在内存中。比如一个进程所需空间进程上下文4M,Data段4M,Stack段4M,总共需要12M,因此虽然虚拟页表还是很大,但是很多都是没有用到的,这些没有用到的页表不应该保存在内存中,而采用两级页表时,只需要保存4个页表,一个顶级页表,一个0-4M、一个4-8M,一个8-12M3个2级页表。顶级页表除了0,其他的页表项Present/absent都会设置为0,每个进程的页表都是独立的
      在这里插入图片描述

      上图a中PT1、PT2分别表示一级页表索引和二级页表索引。上图中一个进程只用3个顶级页表,而其他页表在/不在位被设置为0,当这些不在页表被访问时,会产生一个缺页中断,OS会做处理,这时访问了不该访问的内存。

    • 4级页表,4k的页,每级页表用9位索引,最大支持256TB内存

      2 9 ∗ 2 9 ∗ 2 9 ∗ 2 9 ∗ 2 12 = 2 48 b y t e s 2^9 * 2^9 * 2^9 * 2^9 * 2^{12} = 2^{48} bytes 2

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值