携带标志汇编语言

时间:2015-07-27 20:25:59

标签: assembly x86 masm irvine32 carryflag

为什么此代码中的进位标志设置为255

INCLUDE Irvine32.inc
.data
.code
main PROC

;adding 1 to 255 rolls AL over to zero:
mov al,255
add al,1    ; AL=0, CF=1 (unsigned overflow)
call DumpRegs

;subtracting larger number from smaller:
sub al,1    ; AL=255, CF=1
call DumpRegs

;subtracting 1 from 255
sub al,1    ; AL=254, CF=0
call DumpRegs

exit
main ENDP
END main

也许我得到溢出并且混淆了,但是因为1111 1111是二进制的255,所以不应该只将进位设置为256吗?

2 个答案:

答案 0 :(得分:2)

有两个标志用于跟踪值溢出的时间。

一个是无符号溢出,CF,另一个是带符号溢出OF。

当您执行超出寄存器可容纳的最大值的加法时,CF标志会置1。在你的情况下,任何超过255的添加。

对于减法,同样的事情,反之亦然。如果你减去并且它低于0,那么你得到一个进位。

CF标志允许您在非常大的数字上添加,而无需专门的代码:

add eax, ebx
adc ecx, edx

这将两个32位数字(eax和ebx)加在一起,然后另一组32位数字(ecx,edx)将进位考虑在内。结果是ebx / edx表示64位数。您可以将它用于任何大小的数字(即您可以编写代码以添加两个1024位的数字。)

如果您的号码是无符号的,您可以在末尾添加jc overflow,如果它跳转,则您有溢出(添加后您的号码需要65位。)

OF标志始终设置,但是,它通常仅用于最后一次添加,以便在您的号码被签名时知道您是否有溢出。如果您的号码始终是无符号的,那么您的代码中永远不会使用OF(显然,处理器总是设置OF,无论如何,因为它不知道您是使用有符号还是无符号数字。)

所以在我们之前的补充中,你会这样做:

add eax, ebx
adc ecx, edx
jo overflow

当跳转到溢出时,64位加法不适合64位数。你需要65位。这可用于生成异常并让用户知道他的数学不正确。当然,OF标志可以在AL上工作,在这种情况下,该值被视为介于-128和+127之间的数字。如果add生成大于127的数字,或者减去小于-128的数字,则OF设置。

答案 1 :(得分:1)

nasm语法:

mov al,255 sub al,1

mov al,254 sub al,1

mov al,1 sub al,255

mov al,1 sub al,254

我得到的CF是0,0,1,1

这是你期望的吗?减法实现为反转并加1,你补充第二个数,进位是1而不是零。 0xFF + 0xFE + 1 = 0x1FE,是x86上的减法,它是一个借位,因此对于sub,执行被反转。因此进位标志为0.同样为0xFE + 0xFE + 1.但对于0x01 + 0x00 + 1 = 0x002进0表示进位标志为1. 0x01 + 0x01 + 1 = 0x003进0表示进位1的旗帜。

你确定这些是斧头进入的价值吗?