x86 CPU架构

Posted mathilde27

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了x86 CPU架构相关的知识,希望对你有一定的参考价值。

本文是极客时间《趣谈Linux操作系统》的第6讲笔记, 链接:06 | x86架构:有了开放的架构,才能打造开放的营商环境-极客时间

 Intel的8086 CPU架构

数据单元: 8个16bit 通用寄存器, 后面拓展位32bit

 

 控制单元

IP 寄存器就是指令指针寄存器(Instruction Pointer Register),指向代码段中下一条指令的位置。 

如果需要切换进程呢?每个进程都分代码段和数据段,为了指向不同进程的地址空间,有四个 16 位的段寄存器,分别是 CS、DS、SS、ES。

CS 就是代码段寄存器(Code Segment Register),通过它可以找到代码在内存中的位置

DS 是数据段的寄存器,通过它可以找到数据在内存中的位置。

SS 是栈寄存器(Stack Register)

地址多少bit对应多大的内存?

2^10 = K

2^20 = M

2^30 = G

2^16 = 2^6* 2^10 = 64 K

  • 32 位地址总线,可以访问 2^32=4GB 的内存,一个内存单元是1B, 2^32 = 4*2^30 = 4GB
  • 20位地址总线,可以访问2^20 = 1MB的内存

X86启动时的实模式,智能寻找1M内存,每个段最多64K. 保护模式32位系统,能寻址4G的内存。

总结

cpu架构-x86

IBM8086架构

技术图片

8个16位通用寄存器(CPU 内部的数据单元)

其中的4个AX、BX、CX、DX 为可以分成两个 8 位的寄存器来使用,分别是 AH、AL、BH、BL、CH、CL、DH、DL。

其中 H 就是 High(高位),L 就是 Low(低位)的意思。

 

IP 寄存器

指令指针寄存器(Instruction Pointer Register),指向代码段中下一条指令的位置。

CPU 会根据它来不断地将指令从内存的代码段中,加载到 CPU 的指令队列中,然后交给运算单元去执行。

 

段寄存器

CS -代码段寄存器(Code Segment Register)

通过它可以找到代码在内存中的位置

 

DS -数据段寄存器(Data Segment Register)

通过它可以找到数据在内存中的位置。

 

SS -栈寄存器(Stack Register)

栈是程序运行中一个特殊的数据结构,数据的存取只能从一端进行,秉承后进先出的原则,push 就是入栈,pop 就是出栈。

 

段数据-寻址过程

对于一个段,有一个起始的地址,而段内的具体位置,我们称为偏移量(Offset)。

例如 8 号会议室的第三排,8 号会议室就是起始地址,第三排就是偏移量。

 

背景

在 CS 和 DS 中都存放着一个段的起始地址(16位)

代码段的偏移量在 IP 寄存器中,数据段的偏移量会放在通用寄存器中。

 

偏移量也是 16 位的,但 8086 的地址总线地址是 20 位

 

解决方案

起始地址 *16+ 偏移量

通过这个操作相当于将起始地址左移了4位,再加上偏移量,就能得到一个20位的数据地址了

 

局限

对于只有 20 位地址总线的 8086 来讲,能够区分出的地址也就 2^20=1M,超过这个空间就访问不到了。

如果想访问 1M+X 的地方,这个位置已经超过 20 位了,由于地址总线只有 20 位,在总线上超过 20 位的部分根本是发不出去的,所以发出去的还是 X,最后还是会访问 1M 内的 X 的位置。

在 32 位处理器中,有 32 根地址总线,可以访问 2^32=4G 的内存。

 

进化架构(32bit)

技术图片

通用寄存器

扩展为8个32位的,但为了兼容性,仍然保持了8位和16位的使用方式

指向下一条指令的指令指针寄存器 IP,就会扩展成 32 位的,同样也兼容 16 位的。

 

段寄存器

 

扩展性的局限

因为原来的模式其实有点不伦不类,因为它没有把 16 位当成一个段的起始地址,也没有按 8 位或者 16 位扩展的形式,而是根据当时的硬件,弄了一个不上不下的 20 位的地址。

这样每次都要左移四位,也就意味着段的起始地址不能是任何一个地方,只是能整除 16 的地方。

 

新的定义

CS、SS、DS、ES 仍然是 16 位的,但是不再是段的起始地址。段的起始地址放在内存的某个地方。

这个地方是一个表格,表格中的一项一项是段描述符(Segment Descriptor)。这里面才是真正的段的起始地址。而段寄存器里面保存的是在这个表格中的哪一项,称为选择子(Selector)。

这样,将一个从段寄存器直接拿到的段起始地址,就变成了先间接地从段寄存器找到表格中的一项,再从表格中的一项中拿到段起始地址。这样段起始地址就会很灵活了。

当然为了快速拿到段起始地址,段寄存器会从内存中拿到 CPU 的描述符高速缓存器中。

 

兼容性

32 位的系统架构下,前一种模式称为实模式(Real Pattern),后一种模式称为保护模式(Protected Pattern)。

当系统刚刚启动的时候,CPU 是处于实模式的,这个时候和原来的模式是兼容的。

当需要更多内存的时候,进行一系列的操作,切换到保护模式,就能够用到 32 位 CPU 的特性。

所以事实上是不能无缝兼容的,需要通过切换模式兼容。

 

 

 

 

总体运行图

技术图片

 

以上是关于x86 CPU架构的主要内容,如果未能解决你的问题,请参考以下文章

Linux operation 23Win 10 64位(X86 架构CPU)安装ARM架构的虚拟机(银河麒麟高级服务器操作系统 V10)

[Linux]arm| amd | X86 | aarch64 [转]

Android 逆向x86 CPU 架构体系 ( CPU 模型 | 内存模型 )

Android 逆向x86 CPU 架构体系 ( CPU 模型 | 内存模型 )

CPU处理器架构之争系列(一):英特尔经典x86架构

x86架构初探之8086