如何确定何时设置零标志,符号标志,溢出标志和进位标志?

时间:2016-04-12 20:29:38

标签: assembly

整个国旗的事情让我感到困惑。网上的定义看起来很简单。我似乎无法对这一切得到一个非常好的适用解释。

根据他们的定义, - carry:表示无符号整数溢出 - overflow:表示有符号整数溢出 - 零:操作产生零 - 签名:操作产生负数

那么世界上下面的句子怎么样呢? - 以下说明将设置Sign标志:(这里的答案是252而不是负数。那么为什么设置了标志标志?)

mov al,0FEh
sub al,2
  • 在8位寄存器中添加7Fh和05h会设置溢出标志。(这里的答案是132.它不高于255,为什么会出现溢出?)

  • 在8位寄存器中添加0FFh和05h不会设置溢出标志。(答案是300,那么如何没有溢出标志?它高于256)

  • 在8位寄存器中添加5到0FBh设置零标志(这里的答案是256,而不是0.我理解8位只能保持255但是“0”来自何处?只是不明白。)

有人可以让我知道我在这里做错了什么以及正确的方法是什么? 感谢。

2 个答案:

答案 0 :(得分:7)

  

这里的答案是252而不是负数。那么为什么要设置标志标志?

作为 unsigned ,它是252,但是unsigned没有符号,因此sign标志仅与作为 signed 处理的数字相关。无论你如何处理它,处理器总是处理它与sign标志签名。因此252超过127,因此它在2的补码中是负的,并且符号位被设置。

  

在8位寄存器中添加7Fh和05h设置溢出标志。(这里的答案是132.它不高于255,那么为什么会出现溢出?)

正如您所说,当签名号码溢出时,会设置溢出。带符号的8位变量可以从-128到127.因此,从127到132是溢出。

  

在8位寄存器中添加0FFh和05h不会设置溢出标志。(答案是300,那么如何没有溢出标志?它高于256)

同样,溢出是签名溢出。这会导致无符号溢出,因此将设置进位位。

  

在8位寄存器中添加5到0FBh设置零标志(这里的答案是256,而不是0.我知道8位只能容纳255但是“0”来自哪里?我只是'得到它。)

正如你所说,8位可以达到255.之后溢出,最低的8位为0.因此结果为零,并且设置了零位。

答案 1 :(得分:1)

另一本优秀指南:Understanding Carry vs. Overflow conditions/flags 。它有一些很好的分步示例,带有4位数字,可以很容易地保持整个过程。它还解释了无符号进位是在将这些位解释为无符号时要检查的内容,而有符号溢出是在将这些位解释为有符号时要检查的内容。

基于OP的评论:

  

这是否意味着当8个最低有效位的值为0时真正打开零标志,而不仅仅是“当操作产生0时”

您需要记住的关键是这是固定宽度整数算术。在8位寄存器中,0xFF + 1确实产生0。

在数学术语中,这是modular arithmetic,对于8位操作,模数为2 8

是的,ZF是根据dst = (dst+src) % 0x100设置的。

这是以这种方式设计的,因为通常你只想知道寄存器是否为零,是否在开始为负的寄存器上用inc计数到零,或者你是否正在倒计时注册表开始为正数,为零。

您仍然可以检查CF==0ZF==1,以便在没有携带时获得零的情况下进行检测。 如果ZF仅在dstCF均为零时设置,则通常需要另一条指令来测试结果寄存器。

CF和ZF独立意味着cmpsub后的无符号条件代码如下所示:

JA      Jump if above (CF=0 and ZF=0).
JAE     Jump if above or equal (CF=0).
JB      Jump if below (CF=1).
JBE     Jump if below or equal (CF=1 or ZF=1).

JC      Jump if carry (CF=1).

JE      Jump if equal (ZF=1).

我认为如果ZF只能在没有进位时设置,你就无法分辨出Above和Above-or-Equal 之间的区别。因此,设计决策 not 的最具体原因可能就是你的第一次猜测。

以下是签名比较条件之一:

JLE     Jump  if less or equal (ZF=1 or SF ≠ OF).

完整的条件是英特尔的insn set参考手册(标签wiki中的链接),在jcc(条件代码跳转)指令列表下。