标志寄存器一点细节

标志寄存器一点细节

开始接触汇编时,一个比较容易混淆的问题就是关于标志寄存器的进位和溢出。特别是先入为主地认为运算结果超过寄存器的数值表达范围时就是溢出,这是不对的,这很有可能只是高位进步而不是溢出,列如两个-1相加的情况就是,后面结合负数的补码来分析。一个典型的CPU上,标志寄存器应该有以下这几个状态位,其值对应不同的意义:

Flag    Name                 =1                      =0 
CF      Carry Flag           CY/Carry                NC/No Carry 
PF      Parity Flag          PE/Parity Even          PO/Parity Odd 
AF      Auxiliary Carry      AC/Auxiliary Carry      NA/No Auxiliary Carry 
ZF      Zero Flag            ZR/Zero                 NZ/Not Zero 
SF      Sign Flag            NG/Negative             PL/Positive 
TF      Trace Flag     
IF      Interrupt Flag       EI/Enable Interrupt     DI/Disable Interrupt 
DF      Direction Flag       DN/Down                 UP 
OF      Overflow Flag        OV/Overflow             NV/Not Overflow

进位标志 CF

用于反映运算是否产生进位或借位。如果运算结果的最高位产生一个进位或借位,则CF置1,否则置0。运算结果的最高位包括字操作的第15位和字节操作的第7位。移位指令也会将操作数的最高位或最低位移入CF。

奇偶标志PF

用于反映运算结果低8位中“1”的个数,偶数时则PF置1,否则置0。

辅助进位标志 AF

在字节操作时低半字节向高半字节进位或借位,字操作时低字节向高字节进位或借位,AF置1,否则置0。

零标志 PF

用于判断结果是否为0。运算结果0,ZF置1,否则置0。

符号标志 SF

用于反映运算结果的符号,运算结果为负,SF置1,否则置0。因为有符号数采用补码的形式表示,所以SF与运算结果的最高位相同。

溢出标志 OF

反映有符号数加减运算是否溢出。如果运算结果超过了8位或者16位有符号数的表示范围,则OF置1,否则置0。

跟踪标志 TF

控制标志,当TF被设置位1时,CPU进入单步模式,所谓单步模式就是CPU在每执行一步指令后都产生一个单步中断。主要用于程序的调试。8086/8088中没有专门用来置位和清零TF的命令,需要用其他办法。

中断标志 IF

决定CPU是否响应外部可屏蔽中断请求。IF为1时,CPU允许响应外部的可屏蔽中断请求。

方向标志 DF

决定串操作指令执行时有关指针寄存器调整方向。当DF为1时,串操作指令按递减方式改变有关存储器指针值,每次操作后使SI、DI递减。

结合汇编的分析

先要了解负数的补码表达,有一个方法来解析负数的补码是什么。设想一个展馆,每天到访客流都有个限额,假设最大的额度就是255,刚好是一个字节可以存储的最大值。那么每有一个访客额度就会减一,即表示负一:

1111 1111 - 1 = 1111 1110

这种方法也就是用0来表达1,用1来表达0的反转计数方法。实际上使用的补码是2’补码,即在1’补码的基础上加一,也就是取反加一的补码形式,这样计算机可以用加法器就可以进行减法运算。

首先,在x86平台上,通过Intel可以查询到 mov 指令不影响任何标志位,所以执行它时,标志寄存器的状态不改变。而 add 指令会影响 AF, CF, OF, PF, SF, 和 ZF。 注意32-bit的-1补码即是0xFFFFFFFF,-2补码即是0xFFFFFFFE,0x7FFFFFFF 表示 int 数据的最在正数。

CPU Disasm
Address   Hex dump      Command            Comment
12A4      B0 80         mov al,80
12A6      B2 80         mov dl,80
12A8      00D0          add al,dl          8-bit运算,有进位到ah,溢出,因为结果256不在表达范围;
                                           AF=0, CF=1, OF=1, PF=1, SF=0, ZF=1
12AA      B8 FFFFFFFF   mov eax,-1
12AF      BA FFFFFFFF   mov edx,-1
12B4      01D0          add eax,edx       16-bit运算,最高位有进位但不是溢出,因为结果-2在表达范围;
                                           AF=1, CF=1, OF=0, PF=0, SF=1, ZF=0
12B6      B8 FFFFFF7F   mov eax,7FFFFFFF
12BB      BA FFFFFF7F   mov edx,7FFFFFFF
12C0      01D0          add eax,edx       16-bit运算,无有进位但是溢出,因为两个正数相加结果变成-2;
                                           AF=1, CF=0, OF=1, PF=0, SF=1, ZF=0
12C2      B0 7F         mov al,7F
12C4      B2 7F         mov dl,7F
12C6      00D0          add al,dl          8-bit运算,
                                           AF=1, CF=0, OF=1, PF=0, SF=1, ZF=0

参考资源

  • Intel 80386 Reference Programmer’s Manual
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值