全文是x86汇编,非8086汇编
目录
1.无符号进制转化(√)
- 十进制转换为二进制、八进制、十六进制
小数整数分别进制转换最后拼接
用十进制的数值除以进制得到余数,对余数反向取余
小数部分转换:去掉整数部分,小数部分乘以进制,将得到的整数部分按顺序排列,直到得到题目要求的精度
- 二进制、八进制、十六进制转换为十进制
N...2.1.0.-1.-2.-3
整数部分:2/8/16的n次方*对应数位的数字+。。。。。+2/8/16的0次方*对应数位的数字=
小数部分转换:2/8/16的-1次方*对应数位的数字+。。。。。+2/8/16的-n次方*对应数位的数字=
- 二进制转换成八进制数、十六进制数
整数部分:从小数点前右到左,3/4位依次作为8/16的一位,最左边不够手动凑0,得到的数字直接作为8/16进制的每一位数字
小数部分转换:从小数点后左到右,3/4依次作为8/16的一位,最右边不够手动凑0,,得到的数字直接作为8/16进制的每一位数字
- 八进制、十六进制转换成二进制
每一位转换为3/4位二进制数字,每一位依次转换得到最终结果
- 八进制与十六进制之间的转换
8→2/10→16
2.原码、反码与补码(√)
表示 | 正数 | 负数 |
---|---|---|
原码 | 数据本身的二进制表示(符号位为0) | 数据本身的二进制表示(符号位为1) |
反码 | 和原码一样 | 符号位不变,其余各位按位取反(1变0,0变1) |
补码 | 和原码一样 | 反码加1 |
[+1] = [00000001]原 = [00000001]反 = [00000001]补
[-1] = [10000001]原 = [11111110]反 = [11111111]补
11111111【反码】的补码是:00000001
x是十进制真值,【x】补码才是补码
3.寻址方式(?)
立即数寻址方式
操作数作为指令的一部分而直接写在指令中,这种操作数称为立即数,这种寻址方式也就称为立即数寻址方式。
立即数可以是8位、16位或32位,该数值紧跟在操作码之后。如果立即数为16位或32位,那么,它将按“高高低低”的原则进行存储。例如:
MOV AH, 80H
ADD AX, 1234H
MOV ECX, 123456H
寄存器寻址方式
寄存器寻址方式是一种简单快捷的寻址方式,源和目的操作数都可以是寄存器。
1、源操作数是寄存器寻址方式
如:ADD VARD, EAX
ADD VARW, AX
MOV VARB, BH等。
其中:VARD、VARW和VARB是双字,字和字节类型的内存变量。
2、目的操作数是寄存器寻址方式
如:ADD BH, 78h ADD AX, 1234h MOV EBX, 12345678H等。
3、源和目的操作数都是寄存器寻址方式
如:MOV EAX, EBX MOV AX, BX MOV DH, BL等。
直接寻址方式
立即寻址方式和直接寻址方式的书写格式的不同,直接寻址的地址要写在括号“[”,“]”内。
由于数据段的段寄存器默认为DS,如果要指定访问其它段内的数据,可在指令中用段前缀的方式显式地书写出来。
MOV [1000H], AX ;段寄存器默认为DS
MOV ES:[1000H], AX ;指令的目标操作数就是带有段前缀的直接寻址方式,段寄存器默认为ES
MOV AX, 1234H MOV AX, [1234H] ;前者是立即寻址,后者是直接寻址
MOV AX, VARW MOV AX, [VARW] ;两者是等效的,均为直接寻址
寄存器相对寻址方式
基址寄存器(BX、BP)或变址寄存器(SI、DI)
指令示例:
MOV BX, [SI+100H]
基址加变址寻址方式
其有效地址是一个基址寄存器(BX、BP)和一个变址寄存器(SI、DI)的内容之和。
MOV BX, [BX+SI]
4.标志位
标志位:
PF(parity flag奇偶标志位):用于反映运算结果中“1”的个数的奇偶性,如果“1”的个数为偶数,则PF=1,否则,PF=0。
用法同pf,PE:奇偶校验,pe=1为偶校验,pe=0为奇校验
AF(辅助进位标志位):运算过程中看最后四位,不论长度为多少,最后四位向前有进位或者借位,则AF=1,否则,AF=0。
cf需要是无符号整数,比如ffh(255)+1变成100h(256),超过al(8位)大小,此时al=0,cf=1
对于ax,ffffh(65535)+1,无符号整数的ax(16位)溢出,为0
有符号,7fffh(32767)
对于ax,7fffh+2得到-1
减法的进位标志位,2-3时cf=1,al=ffh(255)
inc eax代表eax自增,dec eax代表eax自减
结果为负数,符号标志位sf为1
8位有符号整数的范围:-128---127,16位有符号整数的范围:-32768---32767
1000h自增是1001,1001h自减是1000h
对26实现neg操作得到-26
5.间接寻址(?)
【通用寄存器】构成简介操作数去
对于数组使用间接操作数:
如果是字节元素大小的数组,遍历数组每次加1即可
如果是2字节元素大小的数组,遍历数组每次加2(byte)即可,同理每个元素是dword(4字节)时,遍历数组每次加4
变址操作数:
6.JMP与LOOP指令
jmp无条件跳转到目标地址
loop,也叫ecx计数器循环,ecx是计数器,每执行一次-1
如果开始循环前,ecx为0,则-1为ffff,ffffh,cx=0,则ffffh
当创建循环嵌套时,最好保存循环的次数
7.堆栈(?)
esp扩展堆栈指针寄存器,使用 call,ret,push,pop进行修改
栈底地址大于栈顶
16位操作数,push操作-2,32位-4;pop增加
ret????call
8.and,or,xor,not,cmp,test,neg(√)
and
可以记成同位相乘
and和or,xor,test都清除溢出和进位标志位;符号标志位、0标志位、奇偶标志位不确定是否更改
or
not
所有位都取反,得补集
or的并集
不影响标志位
xor
如果两个位的值相同得0,不同得1
cmp
隐含操作是:右操作数-左操作数
如果无符号时,结果为正,cf=1,为负,cf=0,二者相等,zf=1
有符号是,见下表
无符号数和有符号数的比较
test
进行and操作,但是不改变操作数
neg
求相反数
neg指令:先得到补码,补码按位取反再+1
9.条件跳转
jmp无条件转移
对于左符号数与右符号数比大小,无符号a(左)大b小,有符号g(左)大l小
je=jz
10.条件循环
LOOPZ/F为零跳转/相等跳转=LOOP指令&zf=1
LOOPNZ/E非零跳转/不等跳转=LOOP指令&zf=0
11.逻辑/算术移动
将最后移出的一位写入CF中
shl/shr/sal都是用0填充,最后覆盖的最高/低位变成cf值
sar算术右移用标志位填充
左移看成原来的数字(十进制)*2^n(移动位数)
右移看成除法
ror/l类似于衔尾蛇,覆盖的原内容从左侧/右侧更新
rcl/r移位,不过原先是衔尾蛇,现在更新的内容变成了最高/低位
12.MUL指令
32位下,mul有三种类型。
- 八位操作数*al
- 16位与ax
- 32位与eax
64位下,64位寄存器/内存操作盒*rax,积放在rdx
乘数与被乘数大小必须一致,都可以寄存器和内存操作数,不可以立即数
mul中是乘数,是单操作数语句,乘积结果是上升以及的ax/eax
如果乘积的高半部分非0,cf和of=1
word是ax,al*al是ax,ax*ax是dx;eax*eax是edx
?????
*2,相当于左移一位 ,但是??????
13.IMUL指令
有符号乘法
单操作数;双操作数:imul 寄存器,寄存器/内存操作数/立即数;
三操作数:imul rax(积),乘数,乘数
如果高半部分不是符号拓展,cf=1和of=1
al一共四位,ax一共八位,eax一共16位,如果想要查看cf/of,应判断前半部分的4/8/16
???
13.DIV指令
被除数只可能是ax/eax
al商,ah余;ax,dx;eax,edx
div单操作数
14.mov指令
两个操作数必须同样大小,不能同时为内存操作数
指令指针寄存器(ip、eip、rip)不能作左操作数
错误写法:mov var2,var1(不能同时为内存操作数)
15.堆栈帧(?)
???????????
16.字符串(?)
在每位之间做and运算
杂
16位通用寄存器不含s结尾以及ip/flag,
32位通用寄存器:ea/b/c/dx+es/di+eb/sp
组合BCD码,是将两位十进制数,存放在一个字节中,例82的存放格式是10000010
操作数的个数:
汇编器生成目标文件,链接器生成可执行文件
BYTE是8位无符号,SBYTE是8位有符号
WORD类型:16位无符号整数;SWORD类型:16位有符号整数
DWORD类型:32位无符号整数;SDWORD类型:32位有符号整数
数据定义的一个例子:
count DWORD 12345
myList DWORD 1,2,3,4,5
addTwo
word=2byte,dword=2字,qword=4字
字节byte=8位
伪指令dd
db:define byte 定义字节型数据 —— 八位数据
dw:define word 定义字型数据 —— 十六位数据
dd:double word 定义双字型数据 —— 三十二位数据
操作符dup
dup是一个操作符,在汇编语言中同dw、db、dd等一样,也是由编译器识别处理的符号。它是和db、dd、dw等数据定义伪指令配合使用的,用来进行数据的重复。
db 3 dup (0) ;定义了三个字节,相当于db 0,0,0 这个0有多大是通过前面的db确定
db 3 dup (0,1,2) ;定义了九个字节,相当于db 0,1,2,0,1,2,0,1,2
db 100 dup ('12') ;重复了100个‘12’
db 3 dup (‘123’,‘abc’)
dup使用格式如下:
dd 重复的次数 dup (重复的双字型数据)
dw 重复的次数 dup (重复的字型数据)
db 重复的次数 dup (重复的字节型数据)
小端排序12345678:78563412低字节在低地址、高字节在高地址
大端排序12345678:12345678
sub指令顺序是:左-右
1、64h的补码表示:0110 0100
2、按位取反:1001 1011
3、末位加1:1001 1100 = 9ch
- -8的原码表示:1000 1000
- -8的反码表示:1111 0111
- -8的补码表示:1111 1000
- 按位取反:0000 0111
- 末位加1:0000 1000 = 8 = 08h
lengthof运算符
sizeof返回byte,即length*byte
offset指令:
mov esi,OFFSET bVal ; ESI = 00404000h
mov esi,OFFSET wVal ; ESI = 00404001h
mov esi,OFFSET dVal ; ESI = 00404003h
mov esi,OFFSET dVal2 ; ESI = 00404007h
OFFSET
也可以应用于直接 - 偏移量操作数。设 myArray 包含 5 个 16 位的字。下面的 MOV 指令首先得到 myArray 的偏移量,然后加 4,再将形成的结果地址直接传送给 ESI。因此,现在可以说 ESI 指向数组中的第 3 个整数。
.data
myArray WORD 1,2,3,4,5
.code
mov esi,OFFSET myArray + 4
inc与dec不影响cf
??????????
??????????
IDATALEN EQU 80H COUNT EQU 25
equ可以看成const count =25,
real4定义单精度,real8定义双精度
TBYTE压缩bcd变量
$当前地址偏移量:
EQU伪指令
PTR运算符
传入数据的一部分
LABEL
将两个数据合并/分开
习题
题型来自对分易三次练习题及一套疑似是真题的卷子
固定题型
1.语句“array word 5 dup(1,2)”分配主存的存储单元个数是:20=2*5*2,此处存储单元数=byte数
2.下面有语法错误的是:
3.or指令可以让操作数若干位不变,若干位置置1,比如:or cx,0000fH
4.and指令可以让操作数若干位不变,若干位置置0,比如:and cx,0fff0H
5.实现数除以2:右移;易错:div是单操作数且只能实现ax/eax除以n;
6.实现数乘2:左移;加上同样大小,
7.88h可以是无符号十进制136(二进制真值),也可以是有符号十进制-120(求补码),压缩型bcd码十进制88
一次性知识点
1.下列存储器,存取速度:寄存器 > Cache > 内存 > 硬盘 > 光盘 > 软盘
2.cpu可以用来描述计算机的磁盘转速
3.在程序执行过程中,EIP寄存器保存的是:下一条要执行指令的地址
4.关于mov指令操作数,正确的是:两个操作数必须同样大小;不能同时为内存操作数(错误:mov val1,val2);指令指针寄存器(ip、eip、rip)不能作左(目标)操作数
5.负数在内存中,以补码方式保存
6.将目标文件生成可执行二进制文件的程序是:链接程序
7.x86汇编语言中,汇编程序常用的三个段:代码段、数据段和堆栈段
8.32位cpu,控制循环次数的寄存器:ecx
9.操作数三种类型:立即数操作数、内存操作数、寄存器操作数
10.一条指令的执行可分为:取指、编码、执行三个阶段
11.一条指令有四个组成部分:标号、指令助记符、操作数、注释,其中标号可分为:数据标号和代码标号,二者负责声明变量和代码块
[标号] 指令助记符 [操作数1] [操作数2] [注释]
数据标号count DWORD 100
代码标号L1: mov ax, bx
12.test进行and操作
13.错误的语法:
inc【esi】
mov ax,PTR value
cmp/mov val1,val2
mov ax,bl
14、