文章目录
3. 系统调用
3.1 用户态与内核态
进程在系统上的运行分为两个级别,用户态和内核态。
用户态的进程可以直接读取用户程序的数据,系统态的进程可以直接访问计算机的任何资源,不受限制。
运行的应用程序基本都是运行在用户态,如果调用操作系统提供的系统态的子功能,就需要系统调用。
3.2 系统调用分类
系统调用,按功能大致分为:
- 设备管理。完成设备的请求、释放、启动等功能。
- 文件管理。完成文件的读、写、创建及删除等功能。
- 进程控制。完成进程的创建、撤销、阻塞及唤醒功能。
- 进程通信。完成进程之间的消息传递或信号传递等功能。
- 内存管理。完成内存的分配、回收,以及获取作业占用内存区大小及地址等功能
3.3 如何从用户态切换到内核态(系统调用举例)
- 用户态进程主动要求切换到内核态的系统调用
- 异常,比如缺页异常
- 外围设备的中断,比如硬盘读写操作完成。
4. 内存管理
4.1 内存管理是做什么的
-
负责内存空间的分配与回收(C++中的malloc函数申请内存,free函数释放内存)
-
从逻辑上对内存空间进行扩充(如4GB内存运行60GB大小的游戏)
-
负责进行地址转换,也就是把逻辑地址转换成相应的物理地址
-
内存保护。保证各进程在各自存储空间内运行,互不干扰。
4.1.1 为什么需要虚拟地址空间
如果没有虚拟地址空间,程序直接访问和操作的都是物理内存。这样会带来两个主要问题:
- 用户程序可以访问任意内存,寻址内存的每个字节,这样就很容易破坏操作系统,造成操作系统崩溃。
- 想要同时运行多个程序特别困难。举个例子:微信在运行的时候给内存地址 1xxx 赋值后,QQ 音乐也同样给内存地址 1xxx 赋值,那么 QQ 音乐对内存的赋值就会覆盖微信之前所赋的值,这就造成了微信这个程序就会崩溃。
4.1.2 使用虚拟地址访问内存有什么优势
- 程序可以使用一系列相邻的虚拟地址来访问物理内存中不相邻的大内存缓冲区。
- 程序可以使用一系列虚拟地址来访问大于可用物理内存的内存缓冲区。
- 不同进程使用的虚拟地址彼此隔离。一个进程中的代码无法更改正在由另一进程或操作系统使用的物理内存。
4.2 常见的内存管理机制
内存管理机制分为连续管理方式(指为一个用户程序分配一个连续的内存空间)和非连续管理方式(指允许一个程序使用的内存有着不相邻的分布)
-
连续分配管理方式
-
分块管理
把内存分为大小相等且固定的几个块,每个进程占用其中的一个。如果进程很小的话,会浪费大量的空间。块式管理已经被淘汰。
-
-
非连续分配管理方式
-
分页管理
把内存分为若干个很小的页面,相比分块,划分的力度更大。分页管理提高了内存利用率,减少内存碎片。
分页管理通过页表对应逻辑地址和物理地址。
分页管理虽然提高了内存利用率,但是“页”无实际意义。
-
分段管理
把内存分为几个大小不固定的、有意义的段,每个段定义了一组逻辑信息。例如,主程序段Main、子程序段X、数据段D、栈段S等。
分段管理通过段表对应逻辑地址和物理地址。
-
段页式管理
段页式管理结合了分段管理和分页管理的优点。把主存先分成若干段,每个段又分成若干页。段与段之间、段的内部(因为是页)都是离散的。
-
4.3 分页管理
4.3.1 基本概念
-
页框:将内存空间分为一个个大小相等的分区(比如每个分区4KB),每个分区就是一个“页框”,或者称为“页帧”、“内存块”、“物理块”
-
页框号:每个页框有一个编号,称为“页框号”,或者“页帧号”、“内存块号”、“物理块号”。页框号从0开始
-
页/页面:
将用户进程的地址空间也分为与页框大小相等的一个个区域,称为“页”或“页面”。每个页面也有一个编号,即“页号”,页号也是从0开始。
一个进程的最后一个页可能并没有页框那么大(这样最后一个页放在页框中会有内部碎片)。因此页框不能太大,避免产生过大的内部碎片。
操作系统以页框为单位为各个进程分配内存空间。进程的每个页面分别放入一个页框中。也就是说,进程的页面与内存的页框有一一对应的关系。
各个页面不必连续存放,也不必按照顺序,可以放到不相邻的页框中。
- 分页管理的虚拟地址分为两部分