存储器
8086系统的主存及其分段模式
计算机的存储器包括主存(也称内存)和辅存(也称外存,如硬盘存储器)。因为CPU只能直接访问计算机的主存,所以,CPU所执行的程序和处理的数据都是存在主存中的, 程序员编程时只需与主存打交道即可。
主存需要有较大的容量,才能使计算机高效地工作。主存容量是以存储单元的数量来计算的。现在,大多数计算机以1字节(8位二进制)的大小来定义一个存储单元,即一个存储单元可以存储一个8位二进制数,并常用以下符号表示存储容量的量级:KB(2^10 字节)、MB (2^20 字节)、GB(2^30 字节)以及TB(2^40 字节)。
为了准确描述数据在主存中的存储位置,计算机系统对主存的每个存储单元(字节)从0开始连续编号,并以此编号来确定存储单元的位置。存储单元编号也称为存储单元的地址,无论是向主存存数据(也称写数据),还是从主存取数据(也称读数据),都必须指出存储单元的地址才行。
地址是存储单元的编号,地址(编号)的位数决定了主存可以拥有的最大存储单元数。一般而言,如果计算机系统的地址位数为n位(二进制位),则其主存的最大容量可以达到2n字节。例如,8086系统的主存地址位数是20位,其主存容量最大为220字节=1MB;80486系统的主存地址位数是32位,其主存容量最大可达2^32字节=4GB。
地址是在CPU对主存做读/写操作时,由CPU向主存发出的。所以,地址是在CPU中形成的。对8086系统,CPU要形成20位的主存地址,但是,CPU内部用于存放地址信息的寄存器均为16位寄存器(如前所述),无法存放一个完整的主存地址,为此,8086系 统对主存的使用采取了分段模式。
分段模式下,一个段的最大容量被限制在64KB,即2^16字节,因此,在一个段的范围内,只需16位地址就可以准确指出每个存储单元,16位的地址也可以用16位寄存器来存放了。但是,这个16位地址只是相对于一个段的内部来定义的,称为段内地址(或段内偏移地址),并不是20位的主存实际地址(也称主存物理地址),并不能直接用来访问主存。图(段内偏移地址与物理地址的关系)所示为段内偏移地址与主存物理地址的关系。
图(段内偏移地址与物理地址的关系)中,从物理地址处开始,定义了一个段,物理地址i称为该段的段首地址,简称段地址。显然,段内一个存储单元的物理地址是该存储单元的段内偏移地址与该段的段地址之和。由此可见,要得到段内一个存储单元的物理地址,除了需要该存储单元的段内偏移地址,还必须有该段的段地址。也就是说,在8086系统的主存分段模式下,一个存储单元的地址要用段地址和段内偏移地址两部分表示,这样表示的地址也称为逻辑地址,是汇编语言程序设计时所用的地址表示形式。
由于段地址本身是一个20位的物理地址,而CPU中用来存放段地址的段寄存器均为16位寄存器,如何解决这个矛盾呢?为此,8086系统规定,只有能被16整除的物理地址才能作为段地址;这样的物理地址其二进制表示形式有如下特征:
xxxxxxxxxxxxxxxx0000
其中,X表示0或1。由于段地址的最低4位必为0,所以,CPU中的段寄存器实际只存放了段地址的高16位,这就解决了段地址在CPU中的表示问题。而CPU中专设的地址加法器,会在将逻辑地址转换成物理地址时,自动在16位段地址低位部分添加4个0,然后再与段内偏移地址相加。
8086系统中,逻辑地址通常表示为
段地址:段内偏移地址
的格式。设某存储单元的逻辑地址用十六进制表示为138D:0200,求该存储单元的物理地址。
解:首先在段地址低位添0(对十六进制,只需添一个0),得到实际的段首地址138D0H,然后再与段内偏移地址0200H相加
138D0H + 0200H = 13AD0H
所以,该存储单元的物理地址为13AD0H(二进制表示为00010011101011010000)。
数据在主存中的存储方式
8086系统中,根据数据的位数不同,定义了以下几种数据类型。
- 字节类型:数据位数为8位(1字节),在主存中存储时占用1个存储单元。
- 字类型:数据位数为16位(2字节),在主存中存储时占用2个存储单元。
- 双字类型:数据位数为32位(4字节),在主存中存储时占用4个存储单元。
- 四字类型:数据位数为64位(8字节),在主存中存储时占用8个存储单元。
- 十字节类型:数据位数为80位(10字节),在主存中存储时占用10个存储单元。
可见,数据位数均为字节的整数倍;位数多于1字节的,称为多字节数据。一个多字节数据在主存中存储时,需要占用地址连续的多个存储单元,数的低位字节存储在地址较低的存储单元,而该多字节数所占用的最低地址,就作为该数的地址。图(多字节数存储示例)所示为双字数据3A625C89H在主存中的存储情况,该数的地址为21004H。