汇编:英特尔x86-64汇编中的CMOVB指令

时间:2018-11-07 23:15:30

标签: c assembly x86-64

在此汇编代码中,“ cmovb”的作用使我有些困惑

leal   (%rsi, %rsi), %eax  // %eax <- %rsi + %rsi
cmpl   %esi, %edi          // compare %edi and %esi
cmovb  %edi, %eax
ret

的C代码是:

int foo(unsigned int a, unsigned int b)
{
    if(a < b) 
        return a;
    else
        return 2*b;
}

有人可以帮助我了解cmovb在这里的工作方式吗?

2 个答案:

答案 0 :(得分:0)

C MOV B =条件电影(如果低于)(传送标志位)。如果符合条件,则按字面意思进行操作。条件为a<b,移动的值为2*b

ABI将返回值存储在%edi中,因此它首先存储a,然后有条件地用2*b覆盖它。

答案 1 :(得分:0)

就像杰斯特评论这个问题一样,cmov*系列指令是有条件的移动,通过 flags 寄存器与先前的(比较)操作配对。

例如,您可以使用Intel documentation作为x86-64 / AMD64指令集的参考。有条件的移动说明显示在合并卷的第172页。

cmovbcmovnaecmovc的执行方式都相同:如果设置了进位标志,它们会将源操作数移动到目标操作数。否则他们什么都不做。

然后,如果我们看一下前面的影响标志的指令,我们将看到cmp指令(后缀l是AT&T语法的一部分,表示参数是“长整数”)根据两个参数之间的差异来更改标志集。特别是,如果第二个小于第一个(在AT&T语法中),则设置进位标志,否则清除进位标志;否则,将清除进位标志。就像执行减法而不将结果存储在任何地方一样。 (cmp指令也会影响其他标志,但是它们会被代码忽略。)