• 虚拟内存和物理内存


    数据总线

    数据总线是CPU和内存之间传输数据的单元。

    如果主板是一个城市,总线就是公共汽车,而数据总线就是最常见的一种公共汽车,在CPU和内存之间传输比特。

    数据总线的单位是每秒多少MB。

    地址总线

    地址总线是CPU用来管理内存的单元。

    一根地址总线代表1位,位宽是同时能传递二进制数据的数量(位数),也就是说:一次性可以传递0或者1的数量。

    位宽为n,理论寻址范围是2的n次方。比如32的位宽,寻址范围是2的32次方,大约4G,

    我们常说的线性地址空间就是地址总线的寻址范围

    这也是为什么,32位的系统最大支持4G的物理内存(因为最大的线性地址空间就是4G)。

    拓展:我们常说的总线,就是系统总线,是数据总线、地址总线和控制总线的统称。

    线性地址空间

    系统中从0x00000000-0xFFFFFFFF的虚拟存储空间。

    逻辑地址

    程序中由程序员指定的地址,也就是代码对应的地址。

    逻辑地址由段和偏移量组成。

    内存寻址

    linux系统内存寻址首先是执行分段机制,把逻辑地址转化为线性地址;然后执行分页机制,将线性地址转化为物理地址。

    物理内存

    这个就是电脑中DRAM内存条的大小。

    虚拟内存

    CPU最早的时候,寻址方式采用的是直接访问物理内存。后来才改变为现在所采用的,通过虚拟内存间接的访问物理内存的机制。

    我们知道进程由fork产生,每个进程都有独立的内存空间,这就是常说的用户空间;以及进程共用的内存空间——内核空间。

    一般来说,对于4G的内存,用户空间3G,内核空间1G。

     用户空间可能存在磁盘上,但是内核空间永远在主内存上。

    用户空间的映射方式是通过页表来实现,内核空间的映射方式是通过线性来实现。

    对于64位的系统,寻址空间有2的64次方大小,理论支持非常大的虚拟内存。但是,实际上最大支持的虚拟内存被厂商限制了,比如最大支持64G或者128G。

    如果你的电脑物理内存为8G,但是进程所需要的内存32G,这个时候怎么办呢?

    采用早期的CPU直接访问物理内存的方式,直接死路一条!

    而虚拟内存这种机制,恰好提供了合适的解决方案:

    虚拟内存的大小是物理内存+交换分区的大小,交换分区是在硬盘上划分一个区域来充当内存,一般是物理内存的2倍。

    这样一来,如果笔记本物理内存是8G,设置交换分区为32G,虚拟内存大小就为32G+8G=40G,内存就够用了!(其本质是拆东墙补西墙而已)

    采用虚拟内存这种机制,其运作原理是怎么样的呢?下面来说说:

    计算机会对虚拟内存地址空间(也就是线性地址空间)(32位为4G)分页产生页(page),对物理内存地址空间(假设256M)分页产生页帧(page frame),

    所以呢,在这里,虚拟内存的页数势必要大于物理内存的页帧数。

    在计算机上有一个页表(page table),就是映射虚拟内存页到物理内存页的,更确切的说是页号到页帧号的映射,而且是一对一的映射。

    但是问题来了,虚拟内存页的个数 > 物理内存页帧的个数,岂不是有些虚拟内存页的地址永远没有对应的物理内存地址空间?

    不是的,系统是这样处理的。

    系统有个页面失效(page fault)机制:

    操作系统找到一个最少使用的页帧,让他失效,并把它写入磁盘,这样就有空闲的物理内存空间了。
    随后把需要访问的页放到页帧中,并修改页表中的映射,这样就保证所有的页都有被调度的可能了。

    这就是处理虚拟内存地址到物理内存的步骤。

    而这个工作是由CPU上叫做MMU(内存管理单元)的来负责,需要用到分页表

    一般来说,每个页的大小为4KB,这也是数据块的大小,因为数据块是文件存储的最小单位。

    虚拟内存地址由页号和偏移量组成,页号就是一个编号,用来对应的物理内存地址中页帧这个概念;而偏移量就是页的大小,实际存储数据的空间。

    举个例子,有一个虚拟地址它的页号是4,偏移量是20,那么他的寻址过程是这样的:

    首先到页表中找到页号4对应的页帧号(比如为8),如果页不在内存中,则用失效机制调入页,否则把页帧号和偏移量传给MMU(CPU的内存管理单元)组成一个物理上真正存在的地址,接着就是访问物理内存中的数据了。

  • 相关阅读:
    putty如何退出全屏模式
    maven项目如何生成war文件
    使用web.xml方式加载Spring时,获取Spring context的两种方式
    Mybatis 示例之 SelectKey
    psql主主复制
    【转】angular使用代理解决跨域
    Error: EACCES: permission denied when trying to install ESLint using npm
    Run Code Once on First Load (Concurrency Safe)
    [转]对于BIO/NIO/AIO,你还只停留在烧开水的水平吗
    golang 时间的比较,time.Time的初始值?
  • 原文地址:https://www.cnblogs.com/leomei91/p/7502439.html
Copyright © 2020-2023  润新知