汇编 | CPU物理地址本质理解
物理地址
我们知道,CPU访问内存单元时,要给出内存单元的地址。所有的内存单元构成的存储空间是一个一维的线性空间,每一个内存单元在这个空间中都有唯一的地址,我们将这个唯一的地址称为物理地址。
CPU通过地址总线送入存储器的,必须是一个内存单元的物理地址。在CPU向地址总线上发出物理地址之前,必须要在内部先形成这个物理地址。不同的CPU可以有不同的形成物理地址的方式。我们现在讨论8086CPU是如何在内部形成内存单元的物理地址的。
16位结构的CPU
我们说8086CPU的上一代CPU(8080, 8085)等是8位机,而8086是16位机,也可以说8086是16位结构的CPU。那么什么是16位结构的CPU呢?
概括地讲,16位结构(16位机、字长为16位等常见说法,与16位结构的含义相同)描述了一个CPU具有下面几方面的结构特性。
运算器一次最多可以处理16位的数据;
寄存器的最大宽度为16位;
寄存器和运算器之间的通路为16位。
8086是16位结构的CPU,这也就是说,在8086内部,能够一次性处理、传输、暂时存储的信息的最大长度是16位的。内存单元的地址在送上地址总线之前,必须在CPU中处理、传输、暂时存放,对于16位CPU,能一次性处理、传输、暂时存储16位的地址。
8086CPU给出物理地址的方法
8086CPU有20位地址总线,可以传送20位地址,达到1MB寻址能力。8086CPU又是16位结构,在内部一次性处理、传输、暂时存储的地址为16位。从8086CPU的内部结构来看,如果将地址从内部简单地发出,那么它只能送出16位的地址,表现出的寻址能力只有64KB
8086CPU采用一种在内部用两个16位地址合成的方法来形成一个20位的物理地址。
8086CPU相关部件的逻辑结构如图2.6所示。
如图2.6所示,当8086CPU要读写内存时:
(1) CPU中的相关部件提供两个16位的地址,一个称为段地址,另一个称为偏移地址;
(2) 段地址和偏移地址通过内部总线送入一个称为地址加法器的部件:
(3) 地址加法器将两个16位地址合成为一个20位的物理地址;
(4) 地址加法器通过内部总线将20位物理地址送入输入输出控制电路;
(5) 输入输出控制电路将20位物理地址送上地址总线;
(6) 20位物理地址被地址总线传送到存储器。
地址加法器采用 物理地址=段地址x16+偏移地址 的方法用段地址和偏移地址合成物理地址。例如,8086CPU要访问地址为123C8H的内存单元,此时,地址加法器的工作过程如图2.7所示(图中数据皆为十一六进制表示)。
由段地址x16引发的讨论
“段地址x16”有一个更为常用的说法是左移4位。计算机中的所有信息都是以二进制的形式存储的,段地址当然也不例外。机器只能处理二进制信息,“左移4位”中的位,指的是二进制位。我们看一个例子,一个数据为2H,二进制形式为10B,对其进行左移运算:
左移位数 二进制 十六进制 十进制
0 10B 2H 2
1 100B 4H 4
2 1000B 8H 8
3 10000B 10H 16
4 100000B 20H 32
观察上面移位次数和各种形式数据的关系,我们可以发现:
-
一个数据的二进制形式左移 \(1\) 位,相当于该数据乘以 \(2\) ;
-
一个数据的二进制形式左移 \(N\) 位,相当于该数据乘以 \(2^N\);
-
地址加法器如何完成段地址 \(\times16\) 的运算? 就是将以二进制形式存放的段地址左移 \(4\) 位。
进一步思考,我们可看出:一个数据的十六进制形式左移 \(1\) 位,相当于乘以 \(16\) ;
一个数据的十进制形式左移 \(1\) 位,相当于乘以 \(10\);
一个 \(X\) 进制的数据左移 \(1\) 位,相当于乘以 \(X\);
注意,下面讨论的是8086CPU段地址和偏移地址的本质含义,而不是为了解决具体的问题而在本质含义之上引申出来的更高级的逻辑意义。
不管以多少种不同的逻辑意义去看待“段地址x16+偏移地址=物理地址”的寻址模式,一定要清楚地知道它的本质含义,这样才能更灵活地利用它来分析、解决问题。如果只拘泥于某一种引申出来的逻辑含义,而模糊本质含义的话,将从意识上限制对这种寻址功能的灵活应用。
“段地址x16+偏移地址=物理地址”的本质含义是:CPU在访问内存时,用一个基础地址(段地址x16)和一个相对于基础地址的偏移地址相加,给出内存单元的物理地址。
更一般地说,8086CPU的这种寻址功能是“基础地址+偏移地址=物理地址”寻址模式的一种具体实现方案。8086CPU中,段地址x16可看作是基础地址。
下面,我们用两个与cPu无关的例子做进一步的比喻说明。
第一个比喻说明“基础地址+偏移地址=物理地址”的思想。
比如说,学校、体育馆、图书馆同在一条笔直的单行路上(参考图2.8),学校位于路的起点(从路的起点到学校距离是0米)。
你要去图书馆,问我那里的地址,我可以用两种方式告诉你图书馆的地址:
(1)从学校走2826m到图书馆。这2826m可以认为是图书馆的物理地址。
(2)从学校走2000m到体育馆,从体育馆再走826m到图书馆。第一个距离2000m是相对于起点的基础地址,第二个距离826m是相对于基础地址的偏移地址(以基础地址为起点的地址)。
第一种方式是直接给出物理地址2826m,而第二种方式是用基础地址和偏移地址相加来得到物理地址的。
第二个比喻进一步说明“段地址x16+偏移地址一物理地址”的思想。
我们为上面的例子加一些限制条件,比如,只能通过纸条来互相通信,你问我图书馆的地址我只能将它写在纸上告诉你。显然,我必须有一张可以容纳4位数据的纸条,才能写下2826这个数据。
可不巧的是,我没有能容纳4位数据的纸条,仅有两张可以容纳3位数据的纸条。这样我只能以这种方式告诉你2826这个数据。
在第一张纸上写上200(段地址),在第二张纸上写上826(偏移地址)。假设我们事前对这种情况又有过相关的约定:你得到这两张纸后,做这样的运算:200(段地址)x10+826(偏移地址=2826(物理地址)。
8086CPU就是这样一个只能提供两张3位数据纸条的CPU