os读书笔记1
系统架构概况
全局描述符表和局部描述符表(GDT和LDT)
这两个表有什么用
进入了保护模式之后,代码段、数据段、堆栈段等内存段不再是通过段寄存器获得段基址即可使用,操作系统把段定义好,记录在全局描述符表。
而局部描述符表则是局部的,它和全局描述符表相比,就相当于一个是一级描述符表(GDT)、一个是二级描述符表(LDT)
表里面存的是什么
描述符表里面保存的都是段描述符,段描述符记录了各个段的信息。如图所示:
其中各个标志位都记录着关于段的不同信息
如何找到GDT和LDT里面的内容
有了段描述符之后,我们就可以定义各种内存段,并保存到GDT和LDT中,此时CPU通过GDTR和LDTR分别查找GDT和LDT表。
GDTR寄存器数据格式如下:
因此GDT中可以容纳段描述符为8192个
这GDTR寄存器初始化需要用到lgdt
定位到某个段描述符,需要用到段选择子
保护模式下段寄存器存入的是段选择子
如此一来,即可找到指定的段,CPU即可从段描述符中取出段基址,再加上段内偏,形成了-段基址:段内偏移地址-的内存访问形式
门描述符
操作系统定义了一套名为门的描述符—调用门、中断门、陷阱门和任务门,门这种描述符提供了一种访问运行在不同于应用程序特权级的系统过程和处理程序的方法。也就是程序/进程/内核之间的交互。
当访问和当前代码段特权相同或特权更高的代码段的时候,通过调用门访问,由调用程序来提供调用门的选择符。
任务状态段和任务门
TSS(如图 1)定义了任务执行环境的状态。这些状态包括通用寄存器、段寄存器、EFLAGS寄存器、EIP 寄存器和段选择符以及三个堆 栈段(特权 0、1、2 各一个堆栈)的指针的状态。它也包括了与任务相应的 LDT 的选择符和页表的基地址。所有运行在保护模式下程序,都是一个称作当前任务的上下文中进行的。当前任务的 TSS的段选择符保存在任务寄存器中。切换到一个任务的最简单的方法是进行 CALL 或 JMP 到那个任务中。新任务的 TSS 的段选择符是通过 CALL 或 JMP 指令给出。在进行任务切换 时,处理器按照下面的次序进行:
-
保存当前 TSS 中当前任务的状态。
-
装载新任务段选择符的任务寄存器。
-
通过 GDT 中段选择符访问新的 TSS。
-
将新 TSS 中新任务的状态装载到通用寄存器、段寄存器、LDTR、控制寄存器 CR3(页表基地址)、EFLAGS 寄存器和 EIP 寄存器。
-
开始执行新任务。
任务也可以通过任务门访,任务门与调用门很相似,除了它是提供(通过选择符)对 TSS 而不是对代码段的访问。
中断与异常处理
外部中断、软件中断和异常是通过中断描述符表(IDT)处理的,
和GDT表类似,在运行中断或异常处理程序的时候,处理器需要先从内部硬件、外部中断控制器、或通过执行INT、INTO、INT 3或BOUND指令的软件中断中接收到一个中断向量。
中断向量内有IDT中的门描述符的索引。
通过IDT表,程序可以执行完中断/异常之后正常返回,切换任务执行。
内存管理
主要有两种形式
-
直接物理地址
-
虚拟内存(通过分页)
使用分页的方式的时候,所有的代码、堆栈、系统段等段都可以将最近访问过页驻留在内存中而进行分页。
页的相关信息保存在两个类型的系统数据结构中:页目录和页表
线性地址则会被分为三个部分:页目录、页表、页框中的偏移量。
一个系统可以有一个或者多个页目录。
系统寄存器
主要分为以下几种
-
EFLAGES寄存器
-
控制寄存器
-
调试寄存器
-
GDTR、LDTR和LDTR寄存器
-
任务寄存器
-
模式相关的寄存器
运行模式
主要有四种
-
保护模式—保护模式是处理器的原生模式,在该模式下,拥有处理器的所有特点和指令,具有最好的性能。对所有新应用程序和操作系统推荐使用该模式
-
实模式—这个模式提供了intel8086的变成模式和一些扩展→比如切换到保护模式或系统管理模式
-
系统管理模式(SSM)—这种模式为操作系统实现电源和OEM专有特征提供了一种透明的机制。SSM模式是通过激活外部系统中断针(SMI#)而进入的,激活产生了一个系统中断(SMI)。在SMM中处理器先保存好当前运行的程序和任务上下文,然后切换到一个单独的地址空间,从SMM返回后处理器再返回SMI之前的状态。
-
虚拟8086模式—在保护模式中,处理器提供了一种准模式叫作虚拟8086模式。这种模式允许在多任务的保护模式下处理执行8086程序。
下图为处理器运行模式之间的转换
EFLAGES寄存器中的系统标志和域
EFLAGES中的系统标志和IOPL域用于控制I/O、可屏蔽硬件中断、调试、任务切换和虚拟8086模式。只有特权代码(通常是操作系统代码)可以修改这些位。
-
TF: 陷阱(第8位)置1是调试状态下的单步执行,置0是禁用单步执行。在单步执行模式下处理器在每条指令后产生一个调试异常,这样在每条指令执行后都可以查看执行程序的状态。如果程序用POPF、POPFD或者IRET指令修改TF标志,那么调试异常就在执行POPF、POPFD或者IRET指令后产生。
-
IF: 中断允许(位9)控制着处理器对可屏蔽硬件中断请求的响应。置1是响应可屏蔽硬件中断,置0为禁止响应可屏蔽硬件中断,IF标志并不影响异常和不可屏蔽中断(NMI)的产生。控制寄存器CR4中的CPL、IOPL和VME标志决定着IF标志是可否可以由指令CLI、STTI、POPF、POPFD和IRET修改。
-
IOPL: I/O特权域(位12和位13)指出当前程序或任务的I/O特权级别。当前程序或任务的CPL必须小于或等于IOPL才可以访问I/O地址空间。当运行在0级特权时,该域只能由的POPF和IRET指令修改。
-
NT: 嵌套任务(位14)控制被中断和被调用的任务的链接。处理器在调用一个由CALL指令、中断或者异常触发的任务时设置该位。当任务因调用IRET指令而返回时,处理器检测并修改该位。该标志可以由POPF/POPFD指令直接置位或清零,然而在应用程序中修改该标志的状态会产生不可预料的异常。
-
RF: 恢复(位16)控制着处理器对断点指令条件的响应。当置1时,该标志可以临时禁用由于指令断点而产生调试异常(#DE),但是其它的异常条件仍可以产生异常。置0时指令断点产生调试异常。RF标志的主要功能是重新执行由指令断点而引发的调试异常后面的指令。
-
VM: 虚拟8086模式(位17)置1进入虚拟8086模式,置0返回保护模式。
-
AC: 对齐检查将该位置1的同时,将控制寄存器中CR0中的AM标志置1就启用了对内存引用的对齐检查。将AC标志和/或AM标志清零就禁用了对齐检查。对齐检查异常只在用户模式(3级特权)下产生。默认特权为0的内存引用,比如段描述表的装载,并不产生这个异常。
-
VIF: 虚拟中断(位 19)包含了一个 IF 标志的虚拟映象。这个标志是和 VIP 标志一起使用的。当控制寄存器 CR4 中的 VME 或者 PVI 标志置为 1 且 IOPL 小于 3 时,处理器只识别 VIF 标志(VME 标志用来启用虚拟 8086 模式扩展,PVI 标志启用保护模式下的虚拟中断)。
-
VIP: 虚拟中断等待(位20)由软件置1表明有一个中断是正在等待被处理,置0表明没有等待处理的中断,该标志和VIF一起使用。处理器读取该标志但从来不修改它,当VME标志或者控制寄存器CR4中的PVI标志置1且IOPL小于3时,处理器只识别VIP标志。
-
ID: 识别(位21)软件置1或0表明是否支持CPUID指令。
内存管理寄存器
处理器中与内存管理有关的寄存器共有四个—GDTR、LDTR、IDTR和TR
全局描述符表寄存器(GDTR)
GDTR寄存器用于保存GDT的32位基地址和16位表界限。基地址指的是GDT的第一个字节的线性地址,而表界限表示GDT中的字节数。LGDT和SGDT指令分别用于加载和保存GDTR寄存器的值。在处理器上电或复位时,基地址默认为0,表界限默认为FFFFH。在进行保护模式的操作时,作为处理器初始化的一部分,需要将新的基地址加载到GDTR中。
局部描述符表寄存器(LDTR)
LDTR寄存器存储了16位的段选择符、32位的基地址、16位的段界限以及LDT描述符的属性。基地址指的是LDT段中第一个字节的线性地址,而段界限表示段中的字节个数。LLDT和SLDT指令专用于加载和保存LDTR寄存器中的段选择符部分。任何包含LDT的段必须在GDT中有一个段描述符。当执行LLDT指令来加载LDTR中的段选择符时,LDT描述符的基地址、界限和属性将自动加载到LDTR中。在进行任务切换时,LDTR会自动加载新任务的段选择符和描述符。在将新的LDT信息写入寄存器之前,LDTR的内容不会自动保存。在处理器上电或复位时,段选择符和基地址都被设为默认值0,段界限被设置为FFFFH。
IDTR中断描述符表寄存器
IDTR寄存器用于保存IDT的32位基地址和16位表界限。基地址指的是IDT中第一个字节的线性地址,而表界限表示IDT中的字节个数。LIDT和SIDT指令专门用于加载和保存IDTR寄存器的值。在处理器上电或复位时,基地址默认为0,表界限默认为FFFFH。作为处理器初始化的一部分,可以修改寄存器中的基地址和表界限。
任务寄存器(TR)
任务寄存器保存着16位的段选择符、32位的基地址、16位的段界限以及当前任务的TSS描述符属性。它引用GDT中的TSS描述符。基地址指示TSS中第一个字节的线性地址,段界限指示TSS中的字节数量。LTR和STR指令专门用于加载和保存任务寄存器中的段选择符部分。当使用LTR指令加载任务寄存器中的段选择符时,基地址、界限和TSS描述符会自动加载到任务寄存器中。处理器上电或复位后,基地址被设置为默认值0,界限被设置为FFFFH。在进行任务切换时,任务寄存器会自动加载新任务的段选择符和TSS描述符。在向任务寄存器写入新内容之前,任务寄存器的内容不会自动保存。
控制寄存器
控制寄存器主要有五个
-
CR0—包含系统控制标志,这些标志控制着处理器的运行模式和状态
-
CR1—保留
-
CR2—包含缺页的线性地址(引起缺页的线性地址)
-
CR3—包含了页目录的基地址和二个标志(PCD和PWT)。该寄存器也被称为页目录基地址寄存器(PDBR)。页目录基地址只有高20位确定,低12位是0,所以页目录地址必须是页边界对齐的(4K字节)。PCD和PWT标志控制着页目录在处理器内部数据缓冲区的缓存(它们不控制TLB页目录信息的缓存)。
-
CR4—包含了一组标志,这些标志启用了架构方面的几个扩展,并指明了系统对某些处理器支持的能力。这个寄存器可以通过MOV指令方式进行读取或修改。在保护模式下MOV指令允许读取或者装载控制寄存器(在0级特权下)。这个限制意味着应用程序或者操作系统过程(运行在1、2、3级特权下)不能读取或者装载控制寄存器。装在控制寄存器时,保留位应该保持以前读取的值。
CPUID识别控制寄存器标志
控制寄存器CR4中的VME、PVI、TSD、DE、PSE、PAE、MCE、PGE、PCE、OSFXSR和OSXMMEXCPT都是与模式相关的。所有的这些标志(除了PCE标志)在使用之前都可以通过CPUID指令来检查他们处理器是否已经实现。
系统指令总汇
指令 | 指令描述 | 对应用程序是否有用 | 应用程序能否执行 |
---|---|---|---|
LLDT | 装载LDT寄存器 | 否 | 是 |
SLDT | 保存LDT寄存器 | 否 | 否 |
LGDT | 装载GDT寄存器 | 否 | 是 |
SGDT | 保存GDT寄存器 | 否 | 否 |
LTR | 装载任务寄存器 | 否 | 是 |
STR | 保存任务寄存器 | 否 | 否 |
LIDT | 装载IDT寄存器 | 否 | 是 |
SIDT | 保存IDT寄存器 | 否 | 否 |
MOV CRn | 装载和保存控制寄存器 | 否 | 是 |
SMSW | 保存MSW | 是 | 否 |
LMSW | 装载MSW | 否 | 是 |
CLTS | 清空CR0中的TS标志 | 否 | 是 |
ARPL | 调整RPL | 是 | 否 |
LAR | 装载访问特权 | 是 | 否 |
LSL | 装载段界限 | 是 | 否 |
VERR | 检验读 | 是 | 否 |
VERW | 检验写 | 是 | 否 |
MOV DBn | 装载和保存调试控制器 | 否 | 是 |
INVD | 使Cache无效,不回写 | 否 | 是 |
WBINVD | 使Cache无效,回写 | 否 | 是 |
INVLPG | 使TLB项无效 | 否 | 是 |
HLT | 停机 | 否 | 是 |
LOCK(前缀) | 总线锁 | 是 | |
RSM | 从系统管理模式返回 | 否 | 是 |
RDMSR3 | 读与模式相关寄存器 | 否 | 是 |
WRMSR3 | 写与模式相关寄存器 | 否 | 是 |
RDPMC4 | 读性能监测计数器 | 是 | 是 |
RDTSC3 | 读时间戳计数器 | 是 | 是 |
tips:
1.对CPL是1或2的应用程序有用
2.由CPL是3的应用程序通过控制寄存器CR4中的TSD和PCE标志访问这些指令
3.这些指令是在IA-32架构中的Pentium处理器引入的
4.这个指令是在IA-32架构中的Pentium Pro 处理器和Pentium® MMX™ 处理器中引入的。