汇编

一、进制

1、十进制

十进制的定义:由十个符号组成,分别是0 1 2 3 4 5 6 7 8 9 逢十进一

2、八进制

八进制的定义:由八个符号组成,分别是0 1 2 3 4 5 6 7 逢八进一

3、十六进制

十六进制的定义:由十六个符号组成,分别是0 1 2 3 4 5 6 7 8 9 A B C D E F

4、二进制与十六进制的关系

任意一个十六进制的符号对应四位二进制的数

二、计算机与数字的关系

1、计算机中的任何信息,比如一张图片、一部视频或者、 一首歌曲, 最终都是以二进制的形式进行存储的。

2、计算机采用二进制的形式存储数据,主要有两方面的原因:

  • 二进制就足够
  • 受硬件制约

三、数据宽度

1、数学上的数字,是没有大小限制的,可以无限的大。但在计算机中,由于受硬件的制约,数据都是有长度限制的(我们称为超过最多宽度的数据会被丢弃)

2、 4位宽度表示:假设计算机只能存储4位2进制数

3、 8位宽度表示:假设计算机只能存储8位2进制数

4、16位宽度表示:假设计算机只能存储16位2进制数

5、 32位宽度表示:假设计算机只能存储32位2进制数

四、计量单位

BYTE 字节 8BIT
WORD 字 16BIT 2字节
DWORD 双字 32BIT 4字节

五、二进制的逻辑运算

1、or运算(有一个为1就是1)

    10110100
or  10001101
___________________
    10111101

2、and运算(两个都是1才是1)

      10110100
and   10001101
________________
      10000100
 

3、 xor运算(不一样为1)

      10110100
xor   10001101
________________
      00111001 

4、not运算(1是0,0是1)

not   10110100
________________
      01001011

5、计算机计算2+3

# 第一步进行异或操作

     0010
xor  0011
_____________
     0001

# 第二步将0001和0011进行与操作


     0001
and  0011
_____________
     0010

# 第三步将0010左移一位进行判断,如果为0000,0001就是结果,不是进行第四步

0010 << 1 = 0100

# 第四步将0001和0100进行异或操作

     0001
xor  0100
————————————
     0101

# 第五步0001和0100进行与操作,然后左移一位进行判断

     0001
and  0100
————————————
     0000

0000 << 1 = 0000

所以答案是0101为5


6、获取某个值的第N位的值


如: 8F
      10001111
and   00001000 
___________________
      00001000

7、最简单的加密算法

要加密的数据: 2015      00100000 00010101
                      01010100 01010100
密钥: 54              ——————————————————
加密后的结果:           01110100 01000001

                          74       41



  
                       01110100 01000001
                       01010100 01010100
                       ——————————————————
                       00100000 00010101
解密后的结果:              20      15

六、32位通用寄存器指定用途


寄存器      主要用途                                 
EAX         累加器                                        
ECX         计数                                            
EDX         I/0指针                                           
EBX         DS段的数据针                                      
ESP         堆栈指针                                        
EBP         SS段的数据指针                           
ESI         字符串操作的源指针; SS段的数据指针              
EDI         字符串操作的且标指针; ES段的数据指针              

七、基本指令

1、界面窗口

2、mov 指令

1、MOV r/m8,r8 r通用寄存器
2、MOV r/m16,r16 m中代表内存
3、MOV r/m32,r32 imm代表立即数
4、MOV r8,r/m8 r8代表8位通用寄存器
5、MOV r16,r/m16 m8代表8位内存
6、MOV r32,r/m32 imm8代表8位立即数
7、MOV r8, imm8
8、MOV r16, im16
9、MOV r32, imm32

MOV目标操作数,源操作数

作用:拷贝源操作数到目标操作数

1、源操作数可以是立即数、通用寄存器、段寄存器、或者内存单元.
2、目标操作数可以是通用寄存器、段寄存器或者内存单元.
3、操作数的宽度必须一样.
4、源操作数和目标操作数不能同时为内存单元.

3、SUB指令

SUB AL,imm8
SUB AX, imm16
SUB EAX, imm32
SUB r/m8,imm8
SUB r/m16, imm16
SUB r/m32, imm32
SUB r/m16,imm8
SUB r/m32,imm8
SUB r/m8,r8
SUB r/m16,r16
SUB r/m32,r32
SUB r8,r/m8
SUB r16, r/m16
SUB r32, r/m32

4、ADD指令

ADD AL, imo8
ADD AX, imm16
ADD EAX, imm32
ADD r/m8,imm8
ADD r/m16, imm16
ADD r/m32, imm32.
ADD r/m16,imm8
ADD r/m32,imm8 .
ADD r/m8,r8
ADD r/m16,r16
ADD r/m32,r32
ADD r8,r/m8
ADD r16,r/m16
ADD r32,r/m32

5、ADN指令

6、OR指令

7、XOR指令

8、NOT指令

八、寄存器与内存的区别

1、寄存器位于CPU内部,执行速度快,但比较贵。

2、内存速度相对较慢,但成本较低,所以可以做的很大。

3、寄存器和内存没有本质区别,都是用于存储数据的容器,都是定宽的。

4、寄存器常用的有8个: EAX、ECX、 EDX、 EBX、ESP、EBP、ESI、 EDI。

5、计算机中的几个常用计量单位: BYTE WORD DWORD

BYTE 字节 = 8(BIT) .
WORD 字 = 16(BIT)
DWORD 双字 = 32(BIT)

1KB = 1024 BYTE
1MB = 1024 KB
1GB = 1024 MB

6、内存的数量特别庞大,无法每个内存单元都起-一个名字,所以用编号来代替,我们称计算机CPU是32位 或者64位,有很多书上说之所以叫32位计算机是因为寄存器的宽度是32位,是不准确的,因为还有很多寄存器是大于32位的。计算机内存的每一个字节会有一个编号(即内存编号的单位是字节),如下:

0x00000000
0x00000001
0x00000002
·········
·········
·········
0xFFFFFFFF

32位计算机内存寻址最大范围:
FFFFFFFF + 1 = 100000000 = 42949672Q6 BYTE = 4194304 kb = 4096 MB = 4 GB

但是可以拓展最大内存

九、内存

mov dword ptr ds: [0x0012FF34], 0x12345678
mov eax, dword ptr ds: [0x0012FF34]
dword :要读/写多少 此时是4字节
byte == 1字节 word == 2字节
ptr: Point代表后面是一个指针(指针的意思就是里面存的不是普通的值,而是个地址)
ds: 段寄存器先不用管记住就行
0x0012FF34:内存编号,必须是32位的前 面0可以省略
注意:地址编号不要随便写,因为内存是有保护的,并不是所有的内存都可以直接读写(需要特别处理),建议地址编号写成esp的值

十、寻址公式

1、寻址公式一

读取内存的值:

MOV EAX, DWORD PTR DS: [0x12FFC4]
MOV EAX, DWORD PTR DS: [0x12FFC8]

向内存中写入数据:

MOV DWORD PTR DS: [0x12FFC4],eax
MOV DWORD PTR DS: [0x12FFC8], ebx

获取内存编号:

LEA EAX, DWORD PTR DS: [0X12FFC4]
LEA EAX, DWORD PTR DS: [ESP+8]

2、寻址公式二

读取内存的值:

MOV ECX, 0x12FFD0
MOV EAX, DWORD PTR DS: [ECX]

向内存中写入数据:

MOV EDX, 0x12FFD8
MOV DWORD PTR DS: [EDX] , 0x87654321

获取内存编号:

LEA EAX, DWORD PTR DS: [EDX]
MOV EAX, DWORD PTR DS: [EDX]

3、寻址公式三

读取内存的值:

MOV ECX, 0x13FFD0
MOV EAX, DWORD PTR DS: [ECX+4]

向内存中写入数据:

MOV EDX, 0x13FFD8
MOV DWORD PTR DS: [EDX+0xC], 0x87654321

获取内存编号:

LEA EAX, DWORD PTR DS: [EDX+4]
MOV EAX, DWORD PTR DS: [EDX+4]

4、寻址公式四([reg+reg* {1,2, 4, 8}])只能乘1,2,4,8其中一个

读取内存的值:

MOV EAX, 13FFC4
MOV ECX, 2
MOV EDX, DWORD PTR DS: [EAX+ECX*4]

向内存中写入数据:

MOV EAX, 13FFC4
MOV ECX, 2
MOV DWORD PTR DS: [EAX+ECX*4], 87654321

获取内存编号:

LEA EAX, DWORD PTR DS: [EAX+ECX*4]

5、寻址公式五([reg+reg* {1, 2, 4, 8]+立即数])

读取内存的值:

MOV EAX, 13FFC4
MOV ECX, 2
MOV EDX, DWORD PTR DS: [EAX+ECX*4+4]

向内存中写入数据:

MOV EAX, 13FFC4
MOV ECX, 2
MOV DWORD PTR DS: [EAX+ECX*4+4], 87654321

获取内存编号:

LEA EAX, DWORD PTR DS: [EAX+ECX*4+2]

十一、pushad和popad

pushad 保存寄存器

popad 恢复寄存器

十二、堆栈

push 栈顶减4(不一定是4,也可能是2),入栈

pop 栈顶加4(不一定是4,也可能是2),出栈

十三、练习

1、先下断点,断点下的位置是窗口弹出

bp MessageBoxA

当输入错误的账号密码时,会弹窗,此时会断下来

2、找到调用函数的位置

当一个函数刚开始执行时,栈顶存储的调用函数返回的地址

3、在账号密码错误时,在下一个断点

4、找到调用函数的位置

5、在跳到弹出成功和失败的位置下断点

6、修改标志寄存器ZF位,并执行

7、为了下次随便输入账号密码也能成功登录将je改为jmp,并保存

十四、标志寄存器

1、CF位(无符号运算时)

进位标志CF(Carry F1ag) :如果运算结果的最高位产生了一个进位或借位,那么,其值为1,否则其值为0。

    11111111
add 00000001
-------------
    00000000

一个8位的数字相加或相减,影响了第九位(进位或借位),CF位值为1

遇到的坑:

2、PF位

奇偶标志PF(Parity Flag):奇偶标志PF用于反映运算结果中“1 ”的个数的奇偶性。如果“1”的个数为偶数,则PF的值为1,否则其值为0。

遇到的坑:

3、AF位

在发生下列情况时,辅助进位标志AF的值被置为1,否则其值为0:

(1)、在字操作时,发生低字节向高字节进位或借位时;
(2)、在字节操作时,发生低4位向高4位进位或借位时。

4、ZF位

零标志2F (Zero Flag):零标志ZF用来反映运算结果是否为0。如果运算结果为0,则其值为1,否则其值为0。在判断运算结果是否为0时,可使用此标志位。

5、SF位

符号标志SF用来反映运算结果的符号位,它与运算结果的最高位相同。

6、OF位

溢出标志0F (Overflow FISg): ``
溢出标志0F用于反映有符号数加减运算所得结果是否溢出。如果运算结果超过当前运算位数所能表示的范围,则称为溢出,OF的值被置为1,否则,OF的值被清为0。
最高位进位与溢出的区别:
进位标志表示无符号数运算结果是否超出范围.
溢出标志表示有符号数运算结果是否超出范围.

遇到的坑:

比如80-48
mov al,8 0
sub al,40

相当于

Mov AL,80
ADD AL, OC0

1000 0000
1100 0000

符号位有进位: 1
最高有效数值位向符号位产生的进位: θ

1 xor θ == 1 所以 0F=1

十四、扩展指令

1、ADC指令

ADC指令:带进位加法
格式: ADC R/M, R/M/IMM
两边不能同时为内存宽度要一样

ADC AL, CL
ADC BYTE PTR DS:[12FFC4],2
ADC BYTE PTR DS:[12FFC4], AL 

2、SBB

SBB指令:带借位减法
格式: SBB R/I, R/M两边不能同时为内存 宽度要一样
SBB AL,CL
SBB BYTE PTR DS: [12FFC4], 2
SBB BYTE PTR DS:[12FFC4], AL

3、XCHG

XCHG 交换数据
格式: XCHG R/M, R/M
两边不能同时为内存宽度要一样

XCHG AL,CL
XCHG DWORD PTR DS: [12FFC4], EAX
XCHG BYTE PTR DS:[12FFC4], AL

4、MOVS指令

MOVS指令:移动数据 内存-内存
BYTE/WORD/DWORD
MOVS BYTE PTR ES: [EDI], BYTE PTR DS:[ESI]
MOVS WORD PTR ES:[EDI], BYTE PTR DS:[ESI]
MOVS DWORD PTR ES:[EDI], BYTE PTR DS:[ESI]

5、STOS指令

STOS指令:将A1/AX/EAX的值存储到[EDI]指定的内存单元

MOV EAX, 12345678
MOV EDI, 12FFC4
STOS BYTE PTR ES: [EDI]
STOS RORD PTR ES: [EDI]
ST0S DAORD PTR ES:[EDI]

6、REP指令

REP指令:按计数寄存器(ECXL) 中指定的次数重复执行字符串指令

十五、JCC

1、jmp

JMP指令:修改EIP的值

JMP 寄存器/立即数

2、call

3、ret

4、CMP

该指令是比较两个操作数,实际上,它相当于SUB指令,但是相减的结果并不保存到第一个操作数中。只是根据相减的结果来改变零标志位的,当两个操作数相等的时候,零标志位置1。

5、test

指令格式: TEST R/M, R/M/IMN

该指令在一定程序上和CMP指令时类似的,两个数值进行与操作,结果不保存,但是会改变相应标志位.

6、JCC

JE, JZ 结果为零则跳转(相等时跳转) ZF=1
JNE,JNZ 结果不为零则跳转(不相等时跳转) ZF=0
JS 结果为负则跳转 SF=1
JNS 结果为非负则跳转 SF=0
JP,JPE 结果中1的个数为偶数则跳转 PF=1
JNP,JPO 结果中1的个数为偶数则跳转 PF=0
J0 结果溢出了则跳转 0F=1
JNO 结果没有溢出则跳转 0F=0
JB,JNAE 小于则跳转(无符号数) CF=1
JNB, JAE 大于等于则跳转(无符号数) CF=0
JBE, JNA 小于等于则跳转(无符号数) CF=1 or ZF=1
JNBE, JA 大于则跳转 (无符号数) CF=0 and ZF=0
JL,JNGE 小于则跳转(有符号数) SF≠OF
JNL,JGE 大于等于则跳转(有符号数) SF=0F
JLE, JNG 小于等于则跳转(有符号数) ZF=1 or SF≠OF
TNLB,TG 大于则跳转(有符号数) ZF=0 and SF=OF

十六、堆栈平衡

1、外平栈

2、函数

计算机的函数,是一个固定的一个程序段,或称其为一个子程序,它在可以实现固定运算功能的同时还带有一入口和一个出口,所谓的入口,就是函数所带的各个参数,我们可以通过这个入口,把函数的参数值代入子程序,供计算机处理,所谓出口,就是指函数的计算结果,也称为返回值,在计算机求得之后,由此口带回给调用它的程序。.

posted @ 2021-11-13 21:56  lnterpreter  阅读(105)  评论(0编辑  收藏  举报