第三章 寄存器(内存访问)
3.1 内存中字的存储
CPU中,用16位寄存器来存储一个字。高8位存放高位字节,低8位存放低位字节。在内存存储中,内存单元式字节单元,那么一个字就需要用俩哥哥地址连续的内存单元来存放,这个字的低位字节存放在低地址单元中,高位字节存放在高地址单元中。这叫小端方式,还有另外一个存放的方式大端方式。
这里就涉及到存储器中数据的组织方式了:
-
大端方式‘
高位字节排放在内存的低地址端,低位字节存放在高地址端 -
小端方式
低位字节存放在内存的低地址端,高位字节存放在高地址端
8086CPU采用的是X86结构,采用小端方式。
然后在读或写一个内存单元里面的数据的时候,需要指定起始地址,读取的长度。读取的长度是一个字还是一个字节。小端方式的起始地址是低地址。
如使用一个立即数ds:[0],这里就要指定 是字还是字节,字节:byte ptr ds:[0],字:word ptr ds:[0]
3.2 DS和[address]
CPU在读写一个内存单元的时候需要给出该内存单元的地址,内存地址由段地址和偏移地址组成。
DS:用来存放数据的段地址
SS:用来存放栈的段地址
CS:用来存放代码的段地址
这里用DS来举例,比如说我们现在要读取10000H单元的内容,段地址为1000H,偏移地址为0H。那么就要用一下的代码来实现。
mov bx,1000H
mov ds,bx
mov al,[0]
像DS这样的段寄存器,不能直接将一个立即数直接MOV到DS中,并且在访问内存单元的时候,必须指定DS以后,通过mov 通用寄存器,[偏移地址]来实现。
将一个数送入内存单元也相似
mov bx,1000H
mov ds,bx
mov [0],al
3.3 字的传送
8086CPU是16位结构,有16根数据线,所以可以一次传送16位数据,就是一个字,只要用mov指令给出16位的寄存器就可以直接进行16位数据的传送。比如
mov bx,1000H
mov ds,bx
mov ax,[0]
mov [0],cx
这里就可以说明小端方式的内存读取的起始地址的问题。
3.4 mov、add、sub指令
-
MOV指令的几种形式
mov 寄存器,数据 比如:mov ax,8
mov 寄存器,寄存器 比如:mov ax,bx
mov 寄存器,内存单元 比如:mov ax,[0]
mov 内存单元,寄存器 比如:mov [0],ax
mov 段寄存器,寄存器 比如:mov ds,ax
mov 内存单元,立即数 比如:mov byte ptr DS:[0], 10
最后一条要注意 给出的内存单元必须指定写入或读取的长度,如byte或word,必须给出段地址:[偏移地址] -
add指令
add ax,8
add ax,bx
add ax,[0]
add [0],ax
add byte(word) ptr ds;[0],9
但是注意的是不能 add 段寄存器,立即数或者寄存器 -
sub指令
和add指令一样,为减指令,用前面一个减去后面一个,结果存在前一个。
3.5 数据段
可以根据需要,将一组内存单元定义为一个段。我们可以将一组长度为N(N<= 64KB)、地址连续、起始地址为16的倍数的内存单元作为专门存储数据的内存单元,从而定义了一个数据段。
如123B0H ~ 123B9H这样的一段内存单元作为数据段,起始地址为123B0H,段地址为123BH,长度为10字节。
3.6 栈
规则:LIFO(Last In First Out,后进先出)
3.7 CPU提供的栈机制
8086CPU 提供入栈和出栈的指令,分别是:PUSH(入栈)和POP(出栈)。比如push ax,将ax的数据送入栈中,pop ax,将栈顶数据取出送入ax中。
现在有俩个问题:
第一:如果我们将10000H ~ 1000FH作为栈空间来使用,CPU如何知道这是栈空间?这个时候就要设置SS(栈段寄存器)的段地址,MOV ax,1000H MOV ss,ax
第二:如何知道栈顶的偏移地址,这个时候就要SP(堆栈指针寄存器)出场,设置SP,MOV sp,0010H。
再8086CPU中 push和pop操作也是符合小端方式存储和取出。
push ax的执行,由以下俩步完成。
(1)SP = SP - 2,SS:SP指向当前栈顶的单元,以当前栈顶前面的单元为新的栈顶;
(2)将ax中的内容送入SS:SP所指向的内存单元处,SS:SP此时指向新的栈顶。
如图
pop ax的执行和push ax的执行正好相反。
(1)将SS:SP指向的内存单元的出书送入ax
(2)SP=SP+2,SS:SP指向当前栈顶下面的单元,以当前栈顶下面的单元为新的栈顶。
如图
3.8 栈顶超界问题
8086CPU不保证对栈的操作会不会出界,这个只能靠自己估算安排。一旦出界可能会修改栈外的内存单元的数据。
3.9 push、pop指令
push和pop指令的格式可以如下:
push 寄存器
pop 寄存器
push 段寄存器
pop 段寄存器
push 内存单元
pop 内存单元