汇编语言操作数类型


x86 的指令格式为:

[label:] mnemonic [operands][ ;comment ]

指令包含的操作数个数可以是:0 个,1 个,2 个或 3 个。这里,为了清晰起见,省略掉标号和注释:

mnemonic
mnemonic [destination]
mnemonic [destination] , [source]
mnemonic [destination] , [source-1] , [source-2]

操作数有 3 种基本类型:
  • 立即数——用数字文本表达式
  • 寄存器操作数——使用 CPU 内已命名的寄存器
  • 内存操作数——引用内存位置

下表说明了标准操作数类型,它使用了简单的操作数符号(32 位模式下),这些符号来自 Intel 手册并进行了改编。本教程将用这些符号来描述每条指令的语法。

操作数 说明
reg8 8 位通用寄存器:AH、AL、BH、BL、CH、CL、DH、DL
reg16 16 位通用寄存器:AX、BX、CX、DX、SI、DI、SP、BP
reg32 32 位通用寄存器:EAX、EEX、ECX、EDX、ESI、EDI、ESP、EBP
reg 通用寄存器
sreg 16 位段寄存器:CS、DS、SS、ES、FS、GS
imm 8 位、16 位或 32 位立即数
imm8 8 位立即数,字节型数值
imm16 16 位立即数,字类型数值
imm32 32 位立即数,双字型数值
reg/mem8 8 位操作数,可以是 8 位通用寄存器或内存字节
reg/mem16 16 位立即数,可以是 16 位通用寄存器或内存字
reg/mem32 32 位立即数,可以是 32 位通用寄存器或内存双字
mem 8位、16 位或 32 位内存操作数

直接内存操作数

变量名引用的是数据段内的偏移量。例如,如下变量 varl 的声明表示,该变量的大小类型为字节,值为十六进制的10:
.data
var1 BYTE 10h
可以编写指令,通过内存操作数的地址来解析(查找)这些操作数。假设 var1 的地址偏移量为 10400h。如下指令将该变量的值复制到 AL 寄存器中:
mov al var1
指令会被汇编为下面的机器指令:
A0 00010400
这条机器指令的第一个字节是操作代码(即操作码(opcode))。剩余部分是 var1 的 32 位十六进制地址。虽然编程时有可能只使用数字地址,但是如同 var1 一样的符号标号会让使用内存更加容易。

另一种表示法。一些程序员更喜欢使用下面这种直接操作数的表达方式,因为,括号意味着解析操作:
mov al, [var1]
MASM 允许这种表示法,因此只要愿意就可以在程序中使用。由于多数程序(包括 Microsoft 的程序)印刷时都没有用括号,所以,本书只在出现算术表达式时才使用这种带括号的表示法:
mov al,[var1 + 5]