0%

标志寄存器_JCC

标志寄存器_JCC

标志寄存器

自己学会拆EFL

  1. 进位标志CF(Carry Flag): 如果运算结果的最高位产生了一个进位或借位,要确定数据宽度,比如add al,1 只要al进位了,就会改变标志位

无符号关注CF位

  1. 奇偶标志位PF(Parity Flag): 奇偶标志位PF用于反映运算结果中’1’的个数的奇偶性,如果为偶数,则为1, 反之为0

mov al,3 011
add al,3 110 #P为1
add al,2 1000 #P为0

  1. 辅助进位标志AF(Auxiliary Carry Flag):

以下情况,AF为1,否则为0

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

mov eax,55eeffff
add eax,2
低四位+2进位了,所以AF为1

mov ax,5efe
add ax,2
就看fe进位没,进位了,所以AF为1

注意这里要看bit

  1. 零标志位ZF(Zero Flag):零标志ZF用来反映运算结果是否为0

xor eax,eax 清0同时还会影响标志位
mov eax,0 清0 不影响标志位

  1. 符号标志SF(Sign Flag): 运算结果的符号位,与运算结果最高位相同

mov al,7f
add al,2

  1. 溢出标志OF(Overflow Flag)

进位标志表示无符号数运算结果是否超出范围
溢出主要是给有符号运算使用

  • 正+正=正 如果结果是负数,则说明溢出了
  • 负+负=负 如果结果是整数,则说明溢出了
  • 正+负 永远不会溢出

理解那个圈,那个圈挺有用的

1. 无符号,有符号都不溢出
mov al,8
add al,8

2. 无符号溢出,有符号不溢出

mov al,0ff
add al,2

无符号超过了,溢出,有符号,-1+2 = 1肯定不溢出

3. 无符号不溢出,有符号溢出

mov al,7f
add al,2

有符号,7f和2都是正数,+过后变成负数了,所以溢出了

4. 无符号,有符号都溢出

mov al,0fe
add al,80

fe负数,80负数 加起来是正数,
无符号,也溢出了,超过最大的ff了
  1. 方向标志DF(Direction Flag)

指令

ADC指令带进位加法

ADC R/M,R/M/IMM 两边不能同时为内存,宽度要一样

SBB带借位减法

SBB R/M,R/M/IMM 两边不能同时为内存,宽度要一样

XCHG 交换数据

XCHG R/M, R/M 不能为立即数啊,想想变量a跟1交换是什么鬼

MOVS 移动数据 内存-内存

都是内存
只有edi跟esi能用

movs byte ptr es:[edi],byte ptr ds:[esi]

简写

  • movsb byte
  • movsw word
  • movsd dword

D标志为1,esi跟edi减,D标志为0,+

STOS 将AL/AX/EAX的值存储到[edi]指定的内存单元

stos byte ptr es:[edi]

简写

  • stosb
  • stosw
  • stosd

方向由D位决定

REP 按ecx指定的次数重复执行

mov ecx,10
rep movsd
就是重复movsd 16次

课后练习

熟练记住CF/PF/AF/ZF/SF/OF的位置

汇编练习:

  1. 只影响CF
    mov ax,0xff
    shr ax,1
    shr会将最低位移入cf

mov ax,0xff00
add ax,0x101

要使得最高位进位,低位不进位

  1. 只影响PF
    mov ax,1
    xor ax,2

  2. 只影响AF
    mov al,0x8
    add al,0x8

  3. 只影响SF
    mov ah,0x71
    xor ah,0x80

mov ah,0xf8
add ah,0x5

  1. 只影响OF
    mov al,0x80
    sub al,0x10

mov ax,0x7f00
add ax,0x201
加法只能让S先为1,然后才不会影响标志位的值,负数+负数=正数必定进位

  1. MOVS移动5个字节,5个字,5个双字
    mov edi,0x18FF8C
    mov esi,0x18FFB4
    movs byte ptr es:[edi],byte ptr ds:[esi]
    movs byte ptr es:[edi],byte ptr ds:[esi]
    movs byte ptr es:[edi],byte ptr ds:[esi]
    movs byte ptr es:[edi],byte ptr ds:[esi]
    movs byte ptr es:[edi],byte ptr ds:[esi]


  2. STOS指令存储5个字节,5个字,5个双字

stos byte ptr es:[edi]


  1. 使用REP指令重写7,8题

mov ecx,0x5
rep movs byte ptr es:[edi],byte ptr ds:[esi]

jcc

修改eip

jmp 影响eip的值 jmp reg/imm

call 也影响eip的值 call imm/reg
push 当前指令地址+指令长度地址,mov eip,imm/reg

retn 相当于pop eip

cmp指令

cmp只修改标志寄存器,相当于sub,

作用比较大小,看sf
是否等于0,看zf

test指令

test R/M,R/M/IMM

实质是&
test eax,eax 判断eax是不是0

jcc跳转

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
JO结果溢出了则跳转OF=1
JNO结果没有溢出则跳转OF=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=OF
JLE, JNG小于等于则跳转 (有符号数)ZF=1 or SF≠ OF
JNLE, JG大于则跳转(有符号数)ZF=0 and SF=OF

本文作者:NoOne
本文地址https://noonegroup.xyz/posts/21d61358/
版权声明:转载请注明出处!