x86汇编语言学习(一)基础知识


学习参考资料:《汇编语言》(第三版)清华大学出版社 王爽著

总线

地址总线的宽度决定CPU的寻址能力。一个CPU有N根地址总线,最多可以寻找2N内存单元(B)。
例如:地址总线宽度分别为16根、20根、24根、32根的CPU,寻址能力分别为:64KB,1MB,16MB,4GB.

数据总线的宽度决定CPU与其他器件进行数据传送时的一次数据传送量。一个CPU有N根数据总线,一次可传送一个N位二进制数据。
例如:数据总线宽度分别为8根、16根、32根的CPU,一次可以传送的数据分别为:1B,2B,4B.

控制总线的宽度决定CPU对系统中其他器件的控制能力。有多少根控制总线,意味着CPU提供了多少种对外部器件的控制。

寄存器

8086CPU有14个寄存器:AX、BX、CX、DX、SI、DI、SP、BP、IP、CS、SS、DS、ES、PSW。都是16位的。

通用寄存器

AX、BX、CX、DX
常用来存放一般性的数据。每个都能存储一个16位的数据,也可以分成两个独立的8位寄存器使用,如AX可以分成AH和AL。高8位构成AH,低8位构成AL。

寄存器寄存器中的数据表示的值
AX010011100010000020000(0x4E20)
AH0100111078(0x4E)
AL0010000032(0x20)

在8086CPU中,只有BX、SI、DI、BP这四个寄存器可以用在“[…]”中来进行内存单元的寻址。这四个寄存器可以单独出现,或只能以四种组合出现:BX和SI,BX和DI,BP和SI,BP和DI。而只要在“[…]”中使用BP且没有显性给出段地址,段地址默认在SS中。

段寄存器

CS、DS、SS、ES

8086CPU访问物理内存时,地址加法器采用物理地址=段地址*16+偏移地址的方法用段地址和偏移地址合成物理地址。
本质上的寻址模式是物理地址=基础地址+偏移地址
CS是代码段寄存器,IP是指令指针寄存器。8086CPU从内存CS*16+IP单元开始读取指令并执行,即CPU将CS:IP指向的内容当作指令执行。读取一条指令后,IP中的值会自动增加所读取指令的长度,从而指向下一条指令。
修改CS和IP寄存器可以使用jmp指令,形如“jmp CS:IP”。

DS通常存放要访问的数据的段地址。比如读取0x10000单元的内容。

// Read 0x10000 to al
mov bx, 0x1000
mov ds, bx
mov al, [0]

“[address]”表示一个内存单元,当中的address表示偏移地址,执行指令时,CPU自动取ds的数据作为内存单元的段地址。0x10000用段地址和偏移地址表示为0x1000:0。8086CPU不支持将数据直接送入段寄存器的操作,“mov ds,0x1000”这条指令是非法的。

SS存放栈顶的段地址,SP存放偏移地址,任意时刻,SS:SP指向栈顶元素。8086CPU中,入栈时栈顶从高地址向低地址方向增长。出栈后,SS:SP指向新的栈顶,pop前的栈顶元素依然存在,但已经不在栈中,当再次执行push操作时,SS:SP又指回那个内存单元并在里面写入数据覆盖原有的。8086CPU没有检测栈顶超界问题的机制,需要编程时注意。

一段内存,可以既是代码段,又是数据段,还可以是栈段,也可以什么都不是,关键在于寄存器的设置,即CS、IP、SS、SP、DS的指向。

标志寄存器

PSW 程序状态字。标志寄存器简称flag。结构如下:

1514131211109876543210
OFDFIFTFSFZFAFPFCF

OF:在进行有符号数运算时,如果结果超过了机器所能表示的范围称为溢出,则of=1;否则of=0。
DF:在串处理指令中,控制每次操作后si、di的增减。df=0每次操作后递增,df=1每次操作后递减。
SF:相关指令执行后,其结果是否为负。为负则sf=1;否则sf=0。
ZF:相关指令执行后,其结果是否为0。为0则zf=1;否则zf=0。
PF:相关指令执行后,其结果的所有bit位中1的个数是否为偶数。为偶数则pf=1;否则pf=0。
CF:在无符号数运算时,运算结果的最高有效位是否向更高位进位或从更高位借位。是则cf=1;否则cf=0。

汇编指令

汇编指令是机器码的助记符,有对应的机器码。

mov add sub指令

(简单使用)都带有两个操作对象,结果保存在前一个里。

程序返回

mov ax, 0x4c00
int 0x21

伪指令

没有对应的机器码,由编译器执行,计算机并不执行。

segment ends

段名 segment
:
段名 ends

用来定义一个段

end

标记汇编程序结束

assume

含义是“假设”,假设某一段寄存器和程序中的某一个用segment … ends定义的段相关联。比如:

assume cs:codesg
codesg segment
...
codesg ends
end

codesg是一个自己定义的标号,指代了一个地址,这里作为一个段的名称,最终会被编译、连接程序处理为一个段的段地址。

其他符号

如+、-、*、/等,由编译器识别,没有对应的机器码。

寻址方式

()表示一个寄存器或者一个内存单元中的内容。
EA表示偏移地址。
SA表示段地址。
idata表示常量。

寻址方式含义名称常用格式举例
[idata]EA=idata;SA=(ds)直接寻址[idata]
[bx]EA=(bx);SA=(ds)寄存器间接寻址[bx]
[si]EA=(si);SA=(ds)寄存器间接寻址[bx]
[di]EA=(di);SA=(ds)寄存器间接寻址[bx]
[bp]EA=(bp);SA=(ss)寄存器间接寻址[bx]
[bx+idata]EA=(bx)+idata;SA=(ds)寄存器相对寻址用于结构体 [bx].idata
[si+idata]EA=(si)+idata;SA=(ds)寄存器相对寻址用于数组 idata[si]
[di+idata]EA=(di)+idata;SA=(ds)寄存器相对寻址用于数组 idata[di]
[bp+idata]EA=(bp)+idata;SA=(ss)寄存器相对寻址用于二维数组 [bx][idata]
[bx+si]EA=(bx)+(si);SA=(ds)基址变址寻址用于二维数组 [bx][si]
[bx+di]EA=(bx)+(di);SA=(ds)基址变址寻址用于二维数组 [bx][si]
[bp+si]EA=(bp)+(si);SA=(ss)基址变址寻址用于二维数组 [bx][si]
[bp+di]EA=(bp)+(di);SA=(ss)基址变址寻址用于二维数组 [bx][si]
[bx+si+idata]EA=(bx)+(si)+idata;SA=(ds)相对基址变址寻址用于表格(结构)中的数组项 [bx].idata[si]
[bx+di+idata]EA=(bx)+(di)+idata;SA=(ds)相对基址变址寻址用于表格(结构)中的数组项 [bx].idata[si]
[bp+si+idata]EA=(bp)+(si)+idata;SA=(ss)相对基址变址寻址用于二维数组 idata[bx][si]
[bp+di+idata]EA=(bp)+(di)+idata;SA=(ss)相对基址变址寻址用于二维数组 idata[bx][si]
  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

TheSerendipitous

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值